Skip to content

Commit 22d4fba

Browse files
ayangsterumairk79annieyangbrharrington
authored
ipc: add new tags for v2 spec (#1168)
The updated spec is for the app specific view when running behind a proxy that submits ipc data. --------- Co-authored-by: Umair Khan <[email protected]> Co-authored-by: annieyang <[email protected]> Co-authored-by: Brian Harrington <[email protected]>
1 parent c77d41d commit 22d4fba

File tree

9 files changed

+336
-15
lines changed

9 files changed

+336
-15
lines changed

spectator-ext-aws2/src/test/java/com/netflix/spectator/aws2/SpectatorExecutionInterceptorTest.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -130,7 +130,7 @@ public void successfulRequest() {
130130
Assertions.assertEquals(millis(42), t.totalTime());
131131
Assertions.assertEquals("EC2.DescribeInstances", get(t.id(), "ipc.endpoint"));
132132
Assertions.assertEquals("200", get(t.id(), "http.status"));
133-
Assertions.assertEquals("POST", get(t.id(), "http.method"));
133+
Assertions.assertEquals("post", get(t.id(), "http.method"));
134134
}
135135

136136
@Test

spectator-ext-ipc/src/main/java/com/netflix/spectator/ipc/IpcLogEntry.java

Lines changed: 39 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,7 @@
2929
import java.util.ArrayList;
3030
import java.util.HashMap;
3131
import java.util.List;
32+
import java.util.Locale;
3233
import java.util.Map;
3334
import java.util.concurrent.TimeUnit;
3435
import java.util.function.Function;
@@ -52,6 +53,7 @@ public final class IpcLogEntry {
5253

5354
private String owner;
5455
private IpcResult result;
56+
private IpcSource source;
5557

5658
private String protocol;
5759

@@ -64,6 +66,7 @@ public final class IpcLogEntry {
6466

6567
private String vip;
6668
private String endpoint;
69+
private IpcMethod method;
6770

6871
private String clientRegion;
6972
private String clientZone;
@@ -79,7 +82,6 @@ public final class IpcLogEntry {
7982
private String serverAsg;
8083
private String serverNode;
8184

82-
private String httpMethod;
8385
private int httpStatus;
8486

8587
private String uri;
@@ -208,6 +210,14 @@ public IpcLogEntry withResult(IpcResult result) {
208210
return this;
209211
}
210212

213+
/**
214+
* Set the source for this request. See {@link IpcSource} for more information.
215+
*/
216+
public IpcLogEntry withSource(IpcSource source) {
217+
this.source = source;
218+
return this;
219+
}
220+
211221
/**
212222
* Set the high level status for the request. See {@link IpcStatus} for more
213223
* information.
@@ -307,6 +317,14 @@ public IpcLogEntry withEndpoint(String endpoint) {
307317
return this;
308318
}
309319

320+
/**
321+
* Set the method used for this request. See {@link IpcMethod} for possible values.
322+
*/
323+
public IpcLogEntry withMethod(IpcMethod method) {
324+
this.method = method;
325+
return this;
326+
}
327+
310328
/**
311329
* Set the client region for the request. In the case of the server side this will be
312330
* automatically filled in if the {@link NetflixHeader#Zone} is specified on the client
@@ -459,7 +477,13 @@ public IpcLogEntry withServerNode(String node) {
459477
* Set the HTTP method used for this request.
460478
*/
461479
public IpcLogEntry withHttpMethod(String method) {
462-
this.httpMethod = method;
480+
try {
481+
IpcMethod m = IpcMethod.valueOf(method.toLowerCase(Locale.US));
482+
withMethod(m);
483+
} catch (Exception e) {
484+
// Ignore invalid methods
485+
withMethod(IpcMethod.unknown);
486+
}
463487
return this;
464488
}
465489

@@ -625,6 +649,12 @@ private void putTag(Map<String, String> tags, String k, String v) {
625649
}
626650
}
627651

652+
private void putTag(Map<String, String> tags, String k, Enum<?> v) {
653+
if (v != null) {
654+
putTag(tags, k, v.name());
655+
}
656+
}
657+
628658
private void finalizeFields() {
629659
// Do final checks and update fields that haven't been explicitly set if needed
630660
// before logging.
@@ -685,7 +715,7 @@ private Id createCallId(String name) {
685715
putTag(tags, IpcTagKey.protocol.key(), protocol);
686716
putTag(tags, IpcTagKey.statusDetail.key(), statusDetail);
687717
putTag(tags, IpcTagKey.httpStatus.key(), Integer.toString(httpStatus));
688-
putTag(tags, IpcTagKey.httpMethod.key(), httpMethod);
718+
putTag(tags, IpcTagKey.httpMethod.key(), method);
689719

690720
return registry.createId(name, tags);
691721
}
@@ -855,6 +885,7 @@ void populateMDC() {
855885
putInMDC("uri", uri);
856886
putInMDC("path", path);
857887
putInMDC(IpcTagKey.endpoint.key(), endpoint);
888+
putInMDC(method);
858889

859890
putInMDC(IpcTagKey.owner.key(), owner);
860891
putInMDC(IpcTagKey.protocol.key(), protocol);
@@ -881,10 +912,10 @@ void populateMDC() {
881912
putInMDC(attemptFinal);
882913

883914
putInMDC(result);
915+
putInMDC(source);
884916
putInMDC(status);
885917
putInMDC(IpcTagKey.statusDetail.key(), statusDetail);
886918

887-
putInMDC(IpcTagKey.httpMethod.key(), httpMethod);
888919
putInMDC(IpcTagKey.httpStatus.key(), Integer.toString(httpStatus));
889920
}
890921

@@ -899,6 +930,7 @@ public String toString() {
899930
.addField("protocol", protocol)
900931
.addField("uri", uri)
901932
.addField("path", path)
933+
.addField("method", method)
902934
.addField("endpoint", endpoint)
903935
.addField("vip", vip)
904936
.addField("clientRegion", clientRegion)
@@ -918,11 +950,11 @@ public String toString() {
918950
.addField("attempt", attempt)
919951
.addField("attemptFinal", attemptFinal)
920952
.addField("result", result)
953+
.addField("source", source)
921954
.addField("status", status)
922955
.addField("statusDetail", statusDetail)
923956
.addField("exceptionClass", getExceptionClass())
924957
.addField("exceptionMessage", getExceptionMessage())
925-
.addField("httpMethod", httpMethod)
926958
.addField("httpStatus", httpStatus)
927959
.addField("requestContentLength", requestContentLength)
928960
.addField("responseContentLength", responseContentLength)
@@ -945,6 +977,7 @@ void reset() {
945977
latency = -1L;
946978
owner = null;
947979
result = null;
980+
source = null;
948981
protocol = null;
949982
status = null;
950983
statusDetail = null;
@@ -953,6 +986,7 @@ void reset() {
953986
attemptFinal = null;
954987
vip = null;
955988
endpoint = null;
989+
method = null;
956990
clientRegion = null;
957991
clientZone = null;
958992
clientApp = null;
@@ -965,7 +999,6 @@ void reset() {
965999
serverCluster = null;
9661000
serverAsg = null;
9671001
serverNode = null;
968-
httpMethod = null;
9691002
httpStatus = -1;
9701003
uri = null;
9711004
path = null;
Lines changed: 99 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,99 @@
1+
/*
2+
* Copyright 2024 Netflix, Inc.
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
package com.netflix.spectator.ipc;
17+
18+
import com.netflix.spectator.api.Tag;
19+
20+
public enum IpcMethod implements Tag {
21+
22+
/**
23+
* Represents a unary gRPC method.
24+
*/
25+
unary,
26+
27+
/**
28+
* Represents a client streaming gRPC method.
29+
*/
30+
client_streaming,
31+
32+
/**
33+
* Represents a server streaming gRPC method.
34+
*/
35+
server_streaming,
36+
37+
/**
38+
* Represents a bidirectional streaming gRPC method.
39+
*/
40+
bidi_streaming,
41+
42+
/**
43+
* Represents an HTTP GET request.
44+
*/
45+
get,
46+
47+
/**
48+
* Represents an HTTP POST request.
49+
*/
50+
post,
51+
52+
/**
53+
* Represents an HTTP PUT request.
54+
*/
55+
put,
56+
57+
/**
58+
* Represents an HTTP PATCH request.
59+
*/
60+
patch,
61+
62+
/**
63+
* Represents an HTTP DELETE request.
64+
*/
65+
delete,
66+
67+
/**
68+
* Represents an HTTP OPTIONS request.
69+
*/
70+
options,
71+
72+
/**
73+
* Represents a GraphQL query.
74+
*/
75+
query,
76+
77+
/**
78+
* Represents a GraphQL mutation.
79+
*/
80+
mutation,
81+
82+
/**
83+
* Represents a GraphQL subscription.
84+
*/
85+
subscription,
86+
87+
/**
88+
* Represents a method that is not supported.
89+
*/
90+
unknown;
91+
92+
@Override public String key() {
93+
return IpcTagKey.method.key();
94+
}
95+
96+
@Override public String value() {
97+
return name();
98+
}
99+
}

spectator-ext-ipc/src/main/java/com/netflix/spectator/ipc/IpcMetric.java

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -228,6 +228,43 @@ public enum IpcMetric {
228228
IpcTagKey.protocol,
229229
IpcTagKey.vip
230230
)
231+
),
232+
233+
/**
234+
* V2 - Timer recording the number and latency of outbound requests.
235+
*/
236+
apiClientCall(
237+
"api.client.call",
238+
EnumSet.of(
239+
IpcTagKey.vip,
240+
IpcTagKey.method,
241+
IpcTagKey.endpoint,
242+
IpcTagKey.owner,
243+
IpcTagKey.id,
244+
IpcTagKey.source,
245+
IpcTagKey.result,
246+
IpcTagKey.status,
247+
IpcTagKey.statusDetail
248+
),
249+
EnumSet.noneOf(IpcTagKey.class)
250+
),
251+
252+
/**
253+
* V2 - Timer recording the number and latency of inbound requests.
254+
*/
255+
apiServerCall(
256+
"api.server.call",
257+
EnumSet.of(
258+
IpcTagKey.method,
259+
IpcTagKey.endpoint,
260+
IpcTagKey.owner,
261+
IpcTagKey.id,
262+
IpcTagKey.source,
263+
IpcTagKey.result,
264+
IpcTagKey.status,
265+
IpcTagKey.statusDetail
266+
),
267+
EnumSet.noneOf(IpcTagKey.class)
231268
);
232269

233270
private final String metricName;
Lines changed: 81 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,81 @@
1+
/*
2+
* Copyright 2024 Netflix, Inc.
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
package com.netflix.spectator.ipc;
17+
18+
import com.netflix.spectator.api.Tag;
19+
20+
public enum IpcSource implements Tag {
21+
22+
/**
23+
* No call was made due to errors potentially.
24+
*/
25+
none,
26+
27+
/**
28+
* Data sourced directly from EVCache as the cache implementation (when the exact cache is known).
29+
*/
30+
evcache,
31+
32+
/**
33+
* Data sourced from a cache where the cache implementation is not directly known or abstracted.
34+
*/
35+
cache,
36+
37+
/**
38+
* Static fallback was used to fetch the data.
39+
*/
40+
fallback,
41+
42+
/**
43+
* Response fetched using mesh.
44+
*/
45+
mesh,
46+
47+
/**
48+
* Response fetched directly from the downstream service (or if not known to be mesh).
49+
*/
50+
direct,
51+
52+
/**
53+
* Data sourced from a validation handler that may short-circuit the response immediately for failed validation.
54+
*/
55+
validation,
56+
57+
/**
58+
* Data sourced and returned directly by a filter or interceptor.
59+
*/
60+
filter,
61+
62+
/**
63+
* Data fetched from an in-memory cache.
64+
*/
65+
memory,
66+
67+
/**
68+
* Data sourced from a user defined business logic handler or root data fetcher.
69+
*/
70+
application;
71+
72+
@Override
73+
public String key() {
74+
return IpcTagKey.source.key();
75+
}
76+
77+
@Override
78+
public String value() {
79+
return name();
80+
}
81+
}

0 commit comments

Comments
 (0)