Skip to content

Commit e11b85c

Browse files
committed
Speed up replay of tests with a lot of requests
1 parent b6e4260 commit e11b85c

File tree

1 file changed

+32
-0
lines changed

1 file changed

+32
-0
lines changed

v2/internal/testcommon/vcr/v3/test_recorder.go

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ package v3
77

88
import (
99
"net/http"
10+
"strconv"
1011
"testing"
1112

1213
"github.com/Azure/azure-sdk-for-go/sdk/azcore"
@@ -46,9 +47,14 @@ func NewTestRecorder(
4647
return nil, eris.Wrapf(err, "checking existence of cassette %s", cassetteName)
4748
}
4849

50+
var cas *cassette.Cassette
4951
// Work out whether we are recording or replaying
5052
if cassetteExists {
5153
opts.Mode = recorder.ModeReplayOnly
54+
cas, err = cassette.Load(opts.CassetteName)
55+
if err != nil {
56+
return nil, eris.Wrapf(err, "loading cassette %s", opts.CassetteName)
57+
}
5258
} else {
5359
opts.Mode = recorder.ModeRecordOnly
5460
}
@@ -78,6 +84,7 @@ func NewTestRecorder(
7884
cfg.AzureAuthorityHost = asocloud.DefaultAADAuthorityHost
7985
}
8086

87+
interactionCache := make(map[string]string)
8188
// check body as well as URL/Method (copied from go-vcr documentation)
8289
r.SetMatcher(func(r *http.Request, i cassette.Request) bool {
8390
if !cassette.DefaultMatcher(r, i) {
@@ -86,6 +93,31 @@ func NewTestRecorder(
8693

8794
// verify custom request count header matches, if present
8895
if header := r.Header.Get(CountHeader); header != "" {
96+
reqCount, err := strconv.Atoi(header)
97+
if err != nil {
98+
log.Info("Request count header parse error", CountHeader, header)
99+
}
100+
101+
// If we've already seen 20 of this request, skip ahead to the end of the interaction to save replay time
102+
if reqCount > 20 {
103+
cachedFinalInteraction, ok := interactionCache[r.Method+" "+r.URL.String()]
104+
if ok {
105+
header = cachedFinalInteraction
106+
} else {
107+
// Find the last interaction for this request
108+
for _, interaction := range cas.Interactions {
109+
if !cassette.DefaultMatcher(r, interaction.Request) {
110+
continue
111+
}
112+
// We could parse the header and perform an integer comparison here to find the max,
113+
// but we don't need to because the interactions are stored in-order in the cassette so the
114+
// last interaction we find for this method+url will be the one with the highest count.
115+
header = interaction.Request.Headers.Get(CountHeader)
116+
interactionCache[r.Method+" "+r.URL.String()] = header
117+
}
118+
}
119+
}
120+
89121
interactionHeader := i.Headers.Get(CountHeader)
90122
if header != interactionHeader {
91123
log.Info("Request count header mismatch", CountHeader, header, "interaction", interactionHeader)

0 commit comments

Comments
 (0)