Skip to content

Commit 80c5768

Browse files
committed
Fix ordering of indexScanKeys after TraceID parsing, closes #1808
Signed-off-by: Michael Burman <[email protected]>
1 parent 7d339ef commit 80c5768

File tree

3 files changed

+119
-9
lines changed

3 files changed

+119
-9
lines changed

Diff for: plugin/storage/badger/spanstore/read_write_test.go

+76-9
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,7 @@ import (
2525
"testing"
2626
"time"
2727

28-
"github.com/stretchr/testify/assert"
28+
assert "github.com/stretchr/testify/require"
2929
"github.com/uber/jaeger-lib/metrics"
3030
"go.uber.org/zap"
3131

@@ -587,14 +587,14 @@ func BenchmarkServiceIndexLimitFetch(b *testing.B) {
587587

588588
// Opens a badger db and runs a test on it.
589589
func runLargeFactoryTest(tb testing.TB, test func(tb testing.TB, sw spanstore.Writer, sr spanstore.Reader)) {
590+
assert := assert.New(tb)
590591
f := badger.NewFactory()
591592
opts := badger.NewOptions("badger")
592593
v, command := config.Viperize(opts.AddFlags)
593594

594595
dir := "/mnt/ssd/badger/testRun"
595596
err := os.MkdirAll(dir, 0700)
596-
defer os.RemoveAll(dir)
597-
assert.NoError(tb, err)
597+
assert.NoError(err)
598598
keyParam := fmt.Sprintf("--badger.directory-key=%s", dir)
599599
valueParam := fmt.Sprintf("--badger.directory-value=%s", dir)
600600

@@ -608,22 +608,89 @@ func runLargeFactoryTest(tb testing.TB, test func(tb testing.TB, sw spanstore.Wr
608608
f.InitFromViper(v)
609609

610610
err = f.Initialize(metrics.NullFactory, zap.NewNop())
611-
assert.NoError(tb, err)
611+
assert.NoError(err)
612612

613613
sw, err := f.CreateSpanWriter()
614-
assert.NoError(tb, err)
614+
assert.NoError(err)
615615

616616
sr, err := f.CreateSpanReader()
617-
assert.NoError(tb, err)
617+
assert.NoError(err)
618618

619619
defer func() {
620620
if closer, ok := sw.(io.Closer); ok {
621621
err := closer.Close()
622-
assert.NoError(tb, err)
622+
os.RemoveAll(dir)
623+
assert.NoError(err)
623624
} else {
624-
tb.FailNow()
625+
assert.FailNow("io.Closer not implemented by SpanWriter")
625626
}
626-
627627
}()
628628
test(tb, sw, sr)
629629
}
630+
631+
// TestRandomTraceID from issue #1808
632+
func TestRandomTraceID(t *testing.T) {
633+
runFactoryTest(t, func(tb testing.TB, sw spanstore.Writer, sr spanstore.Reader) {
634+
s1 := model.Span{
635+
TraceID: model.TraceID{
636+
Low: uint64(14767110704788176287),
637+
High: 0,
638+
},
639+
SpanID: model.SpanID(14976775253976086374),
640+
OperationName: "/",
641+
Process: &model.Process{
642+
ServiceName: "nginx",
643+
},
644+
Tags: model.KeyValues{
645+
model.KeyValue{
646+
Key: "http.request_id",
647+
VStr: "first",
648+
VType: model.StringType,
649+
},
650+
},
651+
StartTime: time.Now(),
652+
Duration: 1 * time.Second,
653+
}
654+
err := sw.WriteSpan(&s1)
655+
assert.NoError(t, err)
656+
657+
s2 := model.Span{
658+
TraceID: model.TraceID{
659+
Low: uint64(4775132888371984950),
660+
High: 0,
661+
},
662+
SpanID: model.SpanID(13576481569227028654),
663+
OperationName: "/",
664+
Process: &model.Process{
665+
ServiceName: "nginx",
666+
},
667+
Tags: model.KeyValues{
668+
model.KeyValue{
669+
Key: "http.request_id",
670+
VStr: "second",
671+
VType: model.StringType,
672+
},
673+
},
674+
StartTime: time.Now(),
675+
Duration: 1 * time.Second,
676+
}
677+
err = sw.WriteSpan(&s2)
678+
assert.NoError(t, err)
679+
680+
params := &spanstore.TraceQueryParameters{
681+
StartTimeMin: time.Now().Add(-1 * time.Minute),
682+
StartTimeMax: time.Now(),
683+
ServiceName: "nginx",
684+
Tags: map[string]string{
685+
"http.request_id": "second",
686+
},
687+
}
688+
traces, err := sr.FindTraces(context.Background(), params)
689+
assert.NoError(t, err)
690+
691+
// failed with `second` tag query, but success with `first`
692+
assert.Equal(t, 1, len(traces))
693+
})
694+
695+
assert.True(t, false)
696+
}

Diff for: plugin/storage/badger/spanstore/reader.go

+5
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@ import (
2222
"errors"
2323
"fmt"
2424
"math"
25+
"sort"
2526
"time"
2627

2728
"github.com/dgraph-io/badger"
@@ -291,6 +292,9 @@ func (r *TraceReader) indexSeeksToTraceIDs(query *spanstore.TraceQueryParameters
291292
prevTraceID = traceID
292293
}
293294
}
295+
sort.Slice(ids[i], func(k, h int) bool {
296+
return bytes.Compare(ids[i][k], ids[i][h]) < 0
297+
})
294298
}
295299
return ids, nil
296300
}
@@ -522,6 +526,7 @@ func (r *TraceReader) scanIndexKeys(indexKeyValue []byte, startTimeMin time.Time
522526
}
523527
return nil
524528
})
529+
525530
return indexResults, err
526531
}
527532

Diff for: plugin/storage/badger/spanstore/rw_internal_test.go

+38
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,8 @@ import (
1717
"bytes"
1818
"context"
1919
"encoding/binary"
20+
"math/rand"
21+
"sort"
2022
"testing"
2123
"time"
2224

@@ -212,3 +214,39 @@ func TestMergeJoin(t *testing.T) {
212214
assert.Equal(2, len(merged))
213215
assert.Equal(uint32(2), binary.BigEndian.Uint32(merged[1]))
214216
}
217+
218+
func TestIndexScanReturnOrder(t *testing.T) {
219+
runWithBadger(t, func(store *badger.DB, t *testing.T) {
220+
testSpan := createDummySpan()
221+
cache := NewCacheStore(store, time.Duration(1*time.Hour), true)
222+
sw := NewSpanWriter(store, cache, time.Duration(1*time.Hour), nil)
223+
rw := NewTraceReader(store, cache)
224+
225+
for i := 0; i < 1000; i++ {
226+
testSpan.TraceID = model.TraceID{
227+
High: rand.Uint64(),
228+
Low: uint64(rand.Int63()),
229+
}
230+
testSpan.SpanID = model.SpanID(rand.Uint64())
231+
testSpan.StartTime = testSpan.StartTime.Add(time.Duration(i) * time.Millisecond)
232+
err := sw.WriteSpan(&testSpan)
233+
assert.NoError(t, err)
234+
}
235+
236+
tqp := &spanstore.TraceQueryParameters{
237+
ServiceName: "service",
238+
StartTimeMax: testSpan.StartTime.Add(time.Hour),
239+
StartTimeMin: testSpan.StartTime.Add(-1 * time.Hour),
240+
}
241+
242+
indexSeeks := make([][]byte, 0, 1)
243+
indexSeeks = serviceQueries(tqp, indexSeeks)
244+
245+
ids := make([][][]byte, 0, len(indexSeeks)+1)
246+
247+
indexResults, _ := rw.indexSeeksToTraceIDs(tqp, indexSeeks, ids)
248+
assert.True(t, sort.SliceIsSorted(indexResults[0], func(i, j int) bool {
249+
return bytes.Compare(indexResults[0][i], indexResults[0][j]) < 0
250+
}))
251+
})
252+
}

0 commit comments

Comments
 (0)