-
Notifications
You must be signed in to change notification settings - Fork 905
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
Redact query string values for http client spans #13114
base: main
Are you sure you want to change the base?
Redact query string values for http client spans #13114
Conversation
aba2207
to
608bc78
Compare
arguments("https://github.com#[email protected]", "https://github.com#[email protected]"), | ||
arguments("user1:[email protected]", "user1:[email protected]"), | ||
arguments("https://github.com@", "https://github.com@"), | ||
arguments( |
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 test was (probably inadvertly) removed in #9925.
The test is added again with new test cases.
d8d8dc3
to
c95b161
Compare
...in/java/io/opentelemetry/instrumentation/api/semconv/http/HttpClientAttributesExtractor.java
Show resolved
Hide resolved
...in/java/io/opentelemetry/instrumentation/api/semconv/http/HttpClientAttributesExtractor.java
Outdated
Show resolved
Hide resolved
...in/java/io/opentelemetry/instrumentation/api/semconv/http/HttpClientAttributesExtractor.java
Show resolved
Hide resolved
...in/java/io/opentelemetry/instrumentation/api/semconv/http/HttpClientAttributesExtractor.java
Outdated
Show resolved
Hide resolved
...in/java/io/opentelemetry/instrumentation/api/semconv/http/HttpClientAttributesExtractor.java
Outdated
Show resolved
Hide resolved
...in/java/io/opentelemetry/instrumentation/api/semconv/http/HttpClientAttributesExtractor.java
Outdated
Show resolved
Hide resolved
...in/java/io/opentelemetry/instrumentation/api/semconv/http/HttpClientAttributesExtractor.java
Outdated
Show resolved
Hide resolved
...in/java/io/opentelemetry/instrumentation/api/semconv/http/HttpClientAttributesExtractor.java
Outdated
Show resolved
Hide resolved
...in/java/io/opentelemetry/instrumentation/api/semconv/http/HttpClientAttributesExtractor.java
Show resolved
Hide resolved
...c/main/java/io/opentelemetry/instrumentation/api/incubator/config/internal/CommonConfig.java
Outdated
Show resolved
Hide resolved
...try/instrumentation/api/incubator/builder/internal/DefaultHttpClientInstrumenterBuilder.java
Outdated
Show resolved
Hide resolved
...mentation/api/incubator/semconv/http/HttpClientExperimentalHttpParamsRedactionExtractor.java
Outdated
Show resolved
Hide resolved
...in/java/io/opentelemetry/instrumentation/api/semconv/http/HttpClientAttributesExtractor.java
Outdated
Show resolved
Hide resolved
...in/java/io/opentelemetry/instrumentation/api/semconv/http/HttpClientAttributesExtractor.java
Outdated
Show resolved
Hide resolved
semantic conventions define the same redactions for |
I think it's ok to scope this PR to http client spans since that's the primary issue in Java at least (update the title, the config option is already scoped to http clients) |
I have created #13292 |
@@ -104,11 +112,21 @@ public SpanKey internalGetSpanKey() { | |||
} | |||
|
|||
@Nullable | |||
private static String stripSensitiveData(@Nullable String url) { | |||
private String stripSensitiveData(@Nullable String url) { |
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 this method could still be static
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.
An instance variable is used here:
Line 122 in bfe189b
if (redactQueryParameters) { |
...in/java/io/opentelemetry/instrumentation/api/semconv/http/HttpClientAttributesExtractor.java
Outdated
Show resolved
Hide resolved
...ava/io/opentelemetry/instrumentation/api/semconv/http/HttpClientAttributesExtractorTest.java
Outdated
Show resolved
Hide resolved
"https://service.com?paramA=valA¶mB=valB", | ||
"https://service.com?paramA=valA¶mB=valB"), | ||
arguments( | ||
"https://service.com?AWSAccessKeyId=AKIAIOSFODNN7", |
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.
does not correctly work with https://service.com?AWSAccessKeyId=AKIAIOSFODNN7&a
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.
In this case, the resulting string will be https://service.com?AWSAccessKeyId=AKIAIOSFODNN7&
. The parsing is waiting for a =
before adding new characters.
The parsing was developed with the asumption that the parameter values don't use a reserved character for the percent encoding: https://en.wikipedia.org/wiki/Percent-encoding
For the Signature
parameter, the AWS documentation provides an example with the Signature
value "URL-Encoded to make it suitable for placement in the query string. ": see Creating a signature
part in https://docs.aws.amazon.com/AmazonS3/latest/API/RESTAuthentication.html No encoding is mentioned for AWSAccessKeyId
. So, it may be safe to suppose that AWSAccessKeyId
value does not contain &
.
I have created open-telemetry/semantic-conventions#1916 to clarify. @trask @laurit Waiting for a clarification, is-it a blocker for this PR?
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 have misunderstood this. query?some=query&a&b
is request with 3 parameters some
, a
and b
Have a look at https://url.spec.whatwg.org/#urlencoded-parsing Ideally the redaction process should should redact just the values for parameters like AWSAccessKeyId
and leave rest of the url as it is, even if it includes sequences that are a bit weird like &a
or &&&
.
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.
…tion/api/semconv/http/HttpClientAttributesExtractor.java Co-authored-by: Steve Rao <[email protected]>
…tion/api/semconv/http/HttpClientAttributesExtractor.java Co-authored-by: Lauri Tulmin <[email protected]>
… other experimental options
…tion/api/semconv/http/HttpClientAttributesExtractor.java Co-authored-by: Lauri Tulmin <[email protected]>
f9a1d63
to
4911e83
Compare
edcdb3a
to
5164fe5
Compare
return url; | ||
} | ||
|
||
StringBuilder redactedParameters = new StringBuilder(); |
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'd rename this variable since it also contains non redacted parameters
paramWithValue = false; | ||
inRedactedParamValue = false; | ||
currentParamName.setLength( | ||
0); // To avoid creating a new StringBuilder for each new parameter |
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.
maybe move the comment to previous line to avoid weird wrapping?
@@ -145,4 +163,66 @@ private static String stripSensitiveData(@Nullable String url) { | |||
} | |||
return url.substring(0, schemeEndIndex + 3) + "REDACTED:REDACTED" + url.substring(atIndex); | |||
} | |||
|
|||
private static String redactQueryParameters(String url) { |
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.
maybe
private static String redactQueryParameters(String url) {
int questionMarkIndex = url.indexOf('?');
if (questionMarkIndex == -1 || !containsParamToRedact(url)) {
return url;
}
StringBuilder buffer = new StringBuilder();
// To build a parameter name until we reach the '=' character
// If the parameter name is a one to redact, we will redact the value
StringBuilder currentParamName = new StringBuilder();
for (int i = questionMarkIndex + 1; i < url.length(); i++) {
char currentChar = url.charAt(i);
if (currentChar == '=') {
buffer.append('=');
if (PARAMS_TO_REDACT.contains(currentParamName.toString())) {
buffer.append("REDACTED");
// skip over parameter value
for (; i + 1 < url.length(); i++) {
char c = url.charAt(i + 1);
if (c == '&' || c == '#') {
break;
}
}
}
} else if (currentChar == '&') { // New parameter delimiter
buffer.append(currentChar);
// To avoid creating a new StringBuilder for each new parameter
currentParamName.setLength(0);
} else if (currentChar == '#') { // Reference delimiter
buffer.append(url.substring(i));
break;
} else {
currentParamName.append(currentChar);
buffer.append(currentChar);
}
}
return url.substring(0, questionMarkIndex) + "?" + buffer;
}
is easier to follow
See https://github.com/open-telemetry/semantic-conventions/blob/main/docs/http/http-spans.md