Skip to content

Commit 07743c0

Browse files
llinderAdrian Cole
authored and
Adrian Cole
committed
Adds SpanStore getTraces by DependencyQueryRequest
1 parent 2789049 commit 07743c0

File tree

9 files changed

+270
-28
lines changed

9 files changed

+270
-28
lines changed

zipkin-server/src/main/java/zipkin/server/internal/ZipkinQueryApiV2.java

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,7 @@
3636
import zipkin2.codec.DependencyLinkBytesEncoder;
3737
import zipkin2.codec.SpanBytesEncoder;
3838
import zipkin2.internal.Nullable;
39+
import zipkin2.storage.DependencyQueryRequest;
3940
import zipkin2.storage.QueryRequest;
4041
import zipkin2.storage.StorageComponent;
4142

@@ -120,6 +121,30 @@ public String getTraces(
120121
return new String(writeTraces(SpanBytesEncoder.JSON_V2, traces), UTF_8);
121122
}
122123

124+
// TODO: name this something better
125+
@RequestMapping(value = "/tracesX", method = RequestMethod.GET, produces = APPLICATION_JSON_VALUE)
126+
public String getTracesX(
127+
@RequestParam(value = "parentServiceName") String parentServiceName,
128+
@RequestParam(value = "childServiceName") String childServiceName,
129+
@Nullable @RequestParam(value = "endTs", required = false) Long endTs,
130+
@Nullable @RequestParam(value = "lookback", required = false) Long lookback,
131+
@RequestParam(value = "limit", defaultValue = "10") int limit,
132+
@Nullable @RequestParam(value = "errorOnly") Boolean errorOnly)
133+
throws IOException {
134+
DependencyQueryRequest queryRequest =
135+
DependencyQueryRequest.newBuilder()
136+
.parentServiceName(parentServiceName)
137+
.childServiceName(childServiceName)
138+
.endTs(endTs != null ? endTs : System.currentTimeMillis())
139+
.lookback(lookback != null ? lookback : defaultLookback)
140+
.limit(limit)
141+
.errorsOnly(errorOnly != null ? errorOnly : false)
142+
.build();
143+
144+
List<List<Span>> traces = storage.spanStore().getTraces(queryRequest).execute();
145+
return new String(writeTraces(SpanBytesEncoder.JSON_V2, traces), UTF_8);
146+
}
147+
123148
@RequestMapping(
124149
value = "/trace/{traceIdHex}",
125150
method = RequestMethod.GET,

zipkin-server/src/main/java/zipkin/server/internal/brave/TracingStorageComponent.java

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -20,10 +20,7 @@
2020
import zipkin2.Call;
2121
import zipkin2.DependencyLink;
2222
import zipkin2.Span;
23-
import zipkin2.storage.QueryRequest;
24-
import zipkin2.storage.SpanConsumer;
25-
import zipkin2.storage.SpanStore;
26-
import zipkin2.storage.StorageComponent;
23+
import zipkin2.storage.*;
2724

2825
// public for use in ZipkinServerConfiguration
2926
public final class TracingStorageComponent extends StorageComponent {
@@ -65,6 +62,11 @@ public Call<List<List<Span>>> getTraces(QueryRequest request) {
6562
return new TracedCall<>(tracer, delegate.getTraces(request), "get-traces");
6663
}
6764

65+
@Override
66+
public Call<List<List<Span>>> getTraces(DependencyQueryRequest request) {
67+
return new TracedCall<>(tracer, delegate.getTraces(request), "get-traces");
68+
}
69+
6870
@Override
6971
public Call<List<Span>> getTrace(String traceId) {
7072
return new TracedCall<>(tracer, delegate.getTrace(traceId), "get-trace");

zipkin-storage/cassandra-v1/src/main/java/zipkin2/storage/cassandra/v1/CassandraSpanStore.java

Lines changed: 22 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -17,16 +17,16 @@
1717
import com.datastax.driver.core.Session;
1818
import com.google.common.collect.ContiguousSet;
1919
import com.google.common.collect.Range;
20-
import java.util.ArrayList;
21-
import java.util.LinkedHashSet;
22-
import java.util.List;
23-
import java.util.Set;
20+
21+
import java.util.*;
22+
2423
import org.slf4j.Logger;
2524
import org.slf4j.LoggerFactory;
2625
import zipkin2.Call;
2726
import zipkin2.Call.FlatMapper;
2827
import zipkin2.DependencyLink;
2928
import zipkin2.Span;
29+
import zipkin2.storage.DependencyQueryRequest;
3030
import zipkin2.storage.QueryRequest;
3131
import zipkin2.storage.SpanStore;
3232
import zipkin2.storage.cassandra.internal.call.AggregateCall;
@@ -146,6 +146,24 @@ public Call<List<List<Span>>> getTraces(QueryRequest request) {
146146
return traceIdCall.flatMap(spans.newFlatMapper(request));
147147
}
148148

149+
@Override
150+
public Call<List<List<Span>>> getTraces(DependencyQueryRequest request) {
151+
// TODO: refactor to share this code between different SpanStore implementations
152+
return getDependencies(request.endTs, request.limit).flatMap((links) -> {
153+
for (DependencyLink link : links) {
154+
if (request.parentServiceName.equals(link.parent()) && request.childServiceName.equals(link.child())) {
155+
if (request.errorsOnly) {
156+
return getTraces(link.errorTraceIds());
157+
} else {
158+
return getTraces(link.callTraceIds());
159+
}
160+
}
161+
}
162+
163+
return Call.create(Collections.emptyList());
164+
});
165+
}
166+
149167
@Override
150168
public Call<List<Span>> getTrace(String traceId) {
151169
// make sure we have a 16 or 32 character trace ID

zipkin-storage/cassandra/src/main/java/zipkin2/storage/cassandra/CassandraSpanStore.java

Lines changed: 22 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -17,19 +17,16 @@
1717
import com.datastax.driver.core.Session;
1818
import com.datastax.driver.core.exceptions.DriverException;
1919
import com.datastax.driver.core.utils.UUIDs;
20-
import java.util.ArrayList;
21-
import java.util.LinkedHashMap;
22-
import java.util.LinkedHashSet;
23-
import java.util.List;
24-
import java.util.Map;
20+
21+
import java.util.*;
2522
import java.util.Map.Entry;
26-
import java.util.Set;
27-
import java.util.UUID;
23+
2824
import org.slf4j.Logger;
2925
import org.slf4j.LoggerFactory;
3026
import zipkin2.Call;
3127
import zipkin2.DependencyLink;
3228
import zipkin2.Span;
29+
import zipkin2.storage.DependencyQueryRequest;
3330
import zipkin2.storage.QueryRequest;
3431
import zipkin2.storage.SpanStore;
3532
import zipkin2.storage.cassandra.internal.call.IntersectKeySets;
@@ -143,6 +140,24 @@ public Call<List<List<Span>>> getTraces(QueryRequest request) {
143140
return intersectedTraceIds.flatMap(spans.newFlatMapper(request));
144141
}
145142

143+
@Override
144+
public Call<List<List<Span>>> getTraces(DependencyQueryRequest request) {
145+
// TODO: refactor to share this code between different SpanStore implementations
146+
return getDependencies(request.endTs, request.limit).flatMap((links) -> {
147+
for (DependencyLink link : links) {
148+
if (request.parentServiceName.equals(link.parent()) && request.childServiceName.equals(link.child())) {
149+
if (request.errorsOnly) {
150+
return getTraces(link.errorTraceIds());
151+
} else {
152+
return getTraces(link.callTraceIds());
153+
}
154+
}
155+
}
156+
157+
return Call.create(Collections.emptyList());
158+
});
159+
}
160+
146161
/**
147162
* Creates a call representing one or more queries against {@link
148163
* Schema#TABLE_TRACE_BY_SERVICE_SPAN}. The result will be an aggregate if the input requests's

zipkin-storage/elasticsearch/src/main/java/zipkin2/elasticsearch/ElasticsearchSpanStore.java

Lines changed: 21 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -13,11 +13,8 @@
1313
*/
1414
package zipkin2.elasticsearch;
1515

16-
import java.util.LinkedHashSet;
17-
import java.util.List;
18-
import java.util.Locale;
19-
import java.util.Map;
20-
import java.util.Set;
16+
import java.util.*;
17+
2118
import zipkin2.Call;
2219
import zipkin2.DependencyLink;
2320
import zipkin2.Span;
@@ -26,10 +23,7 @@
2623
import zipkin2.elasticsearch.internal.client.HttpCall;
2724
import zipkin2.elasticsearch.internal.client.SearchCallFactory;
2825
import zipkin2.elasticsearch.internal.client.SearchRequest;
29-
import zipkin2.storage.GroupByTraceId;
30-
import zipkin2.storage.QueryRequest;
31-
import zipkin2.storage.SpanStore;
32-
import zipkin2.storage.StrictTraceId;
26+
import zipkin2.storage.*;
3327

3428
import static java.util.Arrays.asList;
3529

@@ -111,6 +105,24 @@ public Call<List<List<Span>>> getTraces(QueryRequest request) {
111105
return strictTraceId ? result.map(StrictTraceId.filterTraces(request)) : result;
112106
}
113107

108+
@Override
109+
public Call<List<List<Span>>> getTraces(DependencyQueryRequest request) {
110+
// TODO: refactor to share this code between different SpanStore implementations
111+
return getDependencies(request.endTs, request.limit).flatMap((links) -> {
112+
for (DependencyLink link : links) {
113+
if (request.parentServiceName.equals(link.parent()) && request.childServiceName.equals(link.child())) {
114+
if (request.errorsOnly) {
115+
return getTraces(link.errorTraceIds());
116+
} else {
117+
return getTraces(link.callTraceIds());
118+
}
119+
}
120+
}
121+
122+
return Call.create(Collections.emptyList());
123+
});
124+
}
125+
114126
@Override
115127
public Call<List<Span>> getTrace(String traceId) {
116128
// make sure we have a 16 or 32 character trace ID

zipkin-storage/mysql-v1/src/main/java/zipkin2/storage/mysql/v1/MySQLSpanStore.java

Lines changed: 20 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -13,14 +13,12 @@
1313
*/
1414
package zipkin2.storage.mysql.v1;
1515

16+
import java.util.Collections;
1617
import java.util.List;
1718
import zipkin2.Call;
1819
import zipkin2.DependencyLink;
1920
import zipkin2.Span;
20-
import zipkin2.storage.GroupByTraceId;
21-
import zipkin2.storage.QueryRequest;
22-
import zipkin2.storage.SpanStore;
23-
import zipkin2.storage.StrictTraceId;
21+
import zipkin2.storage.*;
2422

2523
import static zipkin2.internal.DateUtil.getDays;
2624
import static zipkin2.internal.HexCodec.lowerHexToUnsignedLong;
@@ -78,6 +76,24 @@ public Call<List<List<Span>>> getTraces(List<String> traceIds) {
7876
return strictTraceId ? result.map(StrictTraceId.filterTraces(traceIds)) : result;
7977
}
8078

79+
@Override
80+
public Call<List<List<Span>>> getTraces(DependencyQueryRequest request) {
81+
// TODO: refactor to share this code between different SpanStore implementations
82+
return getDependencies(request.endTs, request.limit).flatMap((links) -> {
83+
for (DependencyLink link : links) {
84+
if (request.parentServiceName.equals(link.parent()) && request.childServiceName.equals(link.child())) {
85+
if (request.errorsOnly) {
86+
return getTraces(link.errorTraceIds());
87+
} else {
88+
return getTraces(link.callTraceIds());
89+
}
90+
}
91+
}
92+
93+
return Call.create(Collections.emptyList());
94+
});
95+
}
96+
8197
@Override
8298
public Call<List<String>> getServiceNames() {
8399
return getServiceNamesCall.clone();
Lines changed: 127 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,127 @@
1+
/*
2+
* Copyright 2015-2018 The OpenZipkin Authors
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except
5+
* in compliance with the License. You may obtain a copy of the License at
6+
*
7+
* http://www.apache.org/licenses/LICENSE-2.0
8+
*
9+
* Unless required by applicable law or agreed to in writing, software distributed under the License
10+
* is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
11+
* or implied. See the License for the specific language governing permissions and limitations under
12+
* the License.
13+
*/
14+
package zipkin2.storage;
15+
16+
import zipkin2.internal.Nullable;
17+
18+
public final class DependencyQueryRequest {
19+
20+
public Builder toBuilder() { return new Builder(this); }
21+
22+
public static Builder newBuilder() { return new Builder(); }
23+
24+
public static final class Builder {
25+
26+
private String parentServiceName;
27+
private String childServiceName;
28+
private long endTs, lookback;
29+
private int limit;
30+
private boolean errorsOnly;
31+
32+
Builder() {}
33+
34+
Builder(DependencyQueryRequest source) {
35+
parentServiceName = source.parentServiceName;
36+
childServiceName = source.childServiceName;
37+
endTs = source.endTs;
38+
lookback = source.lookback;
39+
limit = source.limit;
40+
errorsOnly = source.errorsOnly;
41+
}
42+
43+
public Builder parentServiceName(String parentServiceName) {
44+
this.parentServiceName = parentServiceName;
45+
return this;
46+
}
47+
48+
public Builder childServiceName(String childServiceName) {
49+
this.childServiceName = childServiceName;
50+
return this;
51+
}
52+
53+
public Builder endTs(long endTs) {
54+
this.endTs = endTs;
55+
return this;
56+
}
57+
58+
public Builder lookback(long lookback) {
59+
this.lookback = lookback;
60+
return this;
61+
}
62+
63+
public Builder limit(int limit) {
64+
this.limit = limit;
65+
return this;
66+
}
67+
68+
public Builder errorsOnly(boolean errorsOnly) {
69+
this.errorsOnly = errorsOnly;
70+
return this;
71+
}
72+
73+
public final DependencyQueryRequest build() {
74+
if ("".equals(parentServiceName)) throw new IllegalArgumentException("parentServiceName == ''");
75+
if ("".equals(childServiceName)) throw new IllegalArgumentException("childServiceName == ''");
76+
if (parentServiceName == null) throw new IllegalArgumentException("parentServiceName == null");
77+
if (childServiceName == null) throw new IllegalArgumentException("childServiceName == null");
78+
if (endTs <= 0) throw new IllegalArgumentException("endTs <= 0");
79+
if (limit <= 0) throw new IllegalArgumentException("limit <= 0");
80+
if (lookback <= 0) throw new IllegalArgumentException("lookback <= 0");
81+
82+
return new DependencyQueryRequest(
83+
parentServiceName,
84+
childServiceName,
85+
endTs,
86+
lookback,
87+
limit,
88+
errorsOnly
89+
);
90+
}
91+
}
92+
93+
public final String parentServiceName;
94+
public final String childServiceName;
95+
public final long endTs, lookback;
96+
public final int limit;
97+
public final Boolean errorsOnly;
98+
99+
private DependencyQueryRequest(
100+
String parentServiceName,
101+
String childServiceName,
102+
long endTs,
103+
long lookback,
104+
int limit,
105+
@Nullable Boolean errorsOnly
106+
) {
107+
this.parentServiceName = parentServiceName;
108+
this.childServiceName = childServiceName;
109+
this.endTs = endTs;
110+
this.lookback = lookback;
111+
this.limit = limit;
112+
this.errorsOnly = errorsOnly;
113+
}
114+
115+
@Override
116+
public String toString() {
117+
return "DependencyQueryRequest{"
118+
+ "parentServiceName=" + parentServiceName + ", "
119+
+ "childServiceName=" + childServiceName + ", "
120+
+ "endTs=" + endTs + ", "
121+
+ "lookback=" + lookback + ", "
122+
+ "limit=" + limit + ", "
123+
+ "errorsOnly=" + errorsOnly
124+
+ "}";
125+
}
126+
127+
}

0 commit comments

Comments
 (0)