github.com/prebid/prebid-server/v2@v2.18.0/endpoints/openrtb2/auction_benchmark_test.go (about) 1 package openrtb2 2 3 import ( 4 "bytes" 5 "fmt" 6 "net/http" 7 "net/http/httptest" 8 "os" 9 "strings" 10 "testing" 11 "time" 12 13 analyticsBuild "github.com/prebid/prebid-server/v2/analytics/build" 14 "github.com/prebid/prebid-server/v2/config" 15 "github.com/prebid/prebid-server/v2/currency" 16 "github.com/prebid/prebid-server/v2/exchange" 17 "github.com/prebid/prebid-server/v2/experiment/adscert" 18 "github.com/prebid/prebid-server/v2/hooks" 19 "github.com/prebid/prebid-server/v2/macros" 20 metricsConfig "github.com/prebid/prebid-server/v2/metrics/config" 21 "github.com/prebid/prebid-server/v2/openrtb_ext" 22 "github.com/prebid/prebid-server/v2/stored_requests/backends/empty_fetcher" 23 "github.com/prebid/prebid-server/v2/usersync" 24 ) 25 26 // benchmarkTestServer returns the header bidding test ad. This response was scraped from a real appnexus server response. 27 func benchmarkTestServer(w http.ResponseWriter, r *http.Request) { 28 w.Write([]byte(`{"id":"some-request-id","seatbid":[{"bid":[{"id":"4625436751433509010","impid":"my-imp-id","price":0.5,"adm":"\u003cscript type=\"application/javascript\" src=\"http://nym1-ib.adnxs.com/ab?e=wqT_3QKABqAAAwAAAwDWAAUBCM-OiNAFELuV09Pqi86EVRj6t-7QyLin_REqLQkAAAECCOA_EQEHNAAA4D8ZAAAAgOtR4D8hERIAKREJoDDy5vwEOL4HQL4HSAJQ1suTDljhgEhgAGiRQHixhQSAAQGKAQNVU0SSBQbwUpgBrAKgAfoBqAEBsAEAuAECwAEDyAEC0AEA2AEA4AEB8AEAigI6dWYoJ2EnLCA0OTQ0NzIsIDE1MTAwODIzODMpO3VmKCdyJywgMjk2ODExMTAsMh4A8JySAvkBIVR6WGNkQWk2MEljRUVOYkxrdzRZQUNEaGdFZ3dBRGdBUUFSSXZnZFE4dWI4QkZnQVlQX19fXzhQYUFCd0FYZ0JnQUVCaUFFQmtBRUJtQUVCb0FFQnFBRURzQUVBdVFFcGk0aURBQURnUDhFQktZdUlnd0FBNERfSkFTZlJKRUdtbi00XzJRRUFBQUFBQUFEd1AtQUJBUFVCBQ8oSmdDQUtBQ0FMVUMFEARMMAkI8ExNQUNBY2dDQWRBQ0FkZ0NBZUFDQU9nQ0FQZ0NBSUFEQVpBREFKZ0RBYWdEdXRDSEJMb0RDVTVaVFRJNk16STNOdy4umgItITh3aENuZzb8ALg0WUJJSUFRb0FEb0pUbGxOTWpvek1qYzPYAugH4ALH0wHyAhAKBkFEVl9JRBIGNCV1HPICEQoGQ1BHARMcBzE5Nzc5MzMBJwgFQ1AFE_B-ODUxMzU5NIADAYgDAZADAJgDFKADAaoDAMADrALIAwDYAwDgAwDoAwD4AwCABACSBAkvb3BlbnJ0YjKYBACoBACyBAwIABAAGAAgADAAOAC4BADABADIBADSBAlOWU0yOjMyNzfaBAIIAeAEAPAE1suTDogFAZgFAKAF_____wUDXAGqBQ9zb21lLXJlcXVlc3QtaWTABQDJBUmbTPA_0gUJCQAAAAAAAAAA2AUB4AUB\u0026s=61dc0e8770543def5a3a77b4589830d1274b26f1\u0026test=1\u0026pp=${AUCTION_PRICE}\u0026\"\u003e\u003c/script\u003e","adid":"29681110","adomain":["appnexus.com"],"iurl":"http://nym1-ib.adnxs.com/cr?id=29681110","cid":"958","crid":"29681110","w":300,"h":250,"ext":{"bidder":{"appnexus":{"brand_id":1,"auction_id":6127490747252132539,"bidder_id":2}}}}],"seat":"appnexus"}],"ext":{"debug":{"httpcalls":{"appnexus":[{"uri":"http://ib.adnxs.com/openrtb2","requestbody":"{\"id\":\"some-request-id\",\"imp\":[{\"id\":\"my-imp-id\",\"banner\":{\"format\":[{\"w\":300,\"h\":250},{\"w\":300,\"h\":600}]},\"ext\":{\"appnexus\":{\"placement_id\":12883451}}}],\"test\":1,\"tmax\":500}","responsebody":"{\"id\":\"some-request-id\",\"seatbid\":[{\"bid\":[{\"id\":\"4625436751433509010\",\"impid\":\"my-imp-id\",\"price\": 0.500000,\"adid\":\"29681110\",\"adm\":\"\u003cscript type=\\\"application/javascript\\\" src=\\\"http://nym1-ib.adnxs.com/ab?e=wqT_3QKABqAAAwAAAwDWAAUBCM-OiNAFELuV09Pqi86EVRj6t-7QyLin_REqLQkAAAECCOA_EQEHNAAA4D8ZAAAAgOtR4D8hERIAKREJoDDy5vwEOL4HQL4HSAJQ1suTDljhgEhgAGiRQHixhQSAAQGKAQNVU0SSBQbwUpgBrAKgAfoBqAEBsAEAuAECwAEDyAEC0AEA2AEA4AEB8AEAigI6dWYoJ2EnLCA0OTQ0NzIsIDE1MTAwODIzODMpO3VmKCdyJywgMjk2ODExMTAsMh4A8JySAvkBIVR6WGNkQWk2MEljRUVOYkxrdzRZQUNEaGdFZ3dBRGdBUUFSSXZnZFE4dWI4QkZnQVlQX19fXzhQYUFCd0FYZ0JnQUVCaUFFQmtBRUJtQUVCb0FFQnFBRURzQUVBdVFFcGk0aURBQURnUDhFQktZdUlnd0FBNERfSkFTZlJKRUdtbi00XzJRRUFBQUFBQUFEd1AtQUJBUFVCBQ8oSmdDQUtBQ0FMVUMFEARMMAkI8ExNQUNBY2dDQWRBQ0FkZ0NBZUFDQU9nQ0FQZ0NBSUFEQVpBREFKZ0RBYWdEdXRDSEJMb0RDVTVaVFRJNk16STNOdy4umgItITh3aENuZzb8ALg0WUJJSUFRb0FEb0pUbGxOTWpvek1qYzPYAugH4ALH0wHyAhAKBkFEVl9JRBIGNCV1HPICEQoGQ1BHARMcBzE5Nzc5MzMBJwgFQ1AFE_B-ODUxMzU5NIADAYgDAZADAJgDFKADAaoDAMADrALIAwDYAwDgAwDoAwD4AwCABACSBAkvb3BlbnJ0YjKYBACoBACyBAwIABAAGAAgADAAOAC4BADABADIBADSBAlOWU0yOjMyNzfaBAIIAeAEAPAE1suTDogFAZgFAKAF_____wUDXAGqBQ9zb21lLXJlcXVlc3QtaWTABQDJBUmbTPA_0gUJCQAAAAAAAAAA2AUB4AUB\u0026s=61dc0e8770543def5a3a77b4589830d1274b26f1\u0026test=1\u0026pp=${AUCTION_PRICE}\u0026\\\"\u003e\u003c/script\u003e\",\"adomain\":[\"appnexus.com\"],\"iurl\":\"http://nym1-ib.adnxs.com/cr?id=29681110\",\"cid\":\"958\",\"crid\":\"29681110\",\"h\": 250,\"w\": 300,\"ext\":{\"appnexus\":{\"brand_id\": 1,\"auction_id\": 6127490747252132539,\"bidder_id\": 2}}}],\"seat\":\"958\"}],\"bidid\":\"8271358638249766712\",\"cur\":\"USD\"}","status":200}]}},"responsetimemillis":{"appnexus":42}}}`)) 29 } 30 31 // benchmarkBuildTestRequest returns a request which fetches the header bidding test ad. 32 func benchmarkBuildTestRequest() *http.Request { 33 request, _ := http.NewRequest("POST", "/openrtb2/auction", strings.NewReader(`{ 34 "id": "some-request-id", 35 "imp": [ 36 { 37 "id": "my-imp-id", 38 "banner": { 39 "format": [ 40 { 41 "w": 300, 42 "h": 250 43 }, 44 { 45 "w": 300, 46 "h": 600 47 } 48 ] 49 }, 50 "ext": { 51 "appnexus": { 52 "placementId": 12883451 53 } 54 } 55 } 56 ], 57 "test": 1, 58 "tmax": 500 59 }`)) 60 return request 61 } 62 63 // BenchmarkOpenrtbEndpoint measures the performance of the endpoint, mocking out the external server dependency. 64 func BenchmarkOpenrtbEndpoint(b *testing.B) { 65 server := httptest.NewServer(http.HandlerFunc(benchmarkTestServer)) 66 defer server.Close() 67 68 var infos = make(config.BidderInfos, 0) 69 infos["appnexus"] = config.BidderInfo{Capabilities: &config.CapabilitiesInfo{Site: &config.PlatformInfo{MediaTypes: []openrtb_ext.BidType{openrtb_ext.BidTypeBanner}}}} 70 paramValidator, err := openrtb_ext.NewBidderParamsValidator("../../static/bidder-params") 71 if err != nil { 72 return 73 } 74 75 nilMetrics := &metricsConfig.NilMetricsEngine{} 76 77 adapters, adaptersErr := exchange.BuildAdapters(server.Client(), &config.Configuration{}, infos, nilMetrics) 78 if adaptersErr != nil { 79 b.Fatal("unable to build adapters") 80 } 81 82 gdprPermsBuilder := fakePermissionsBuilder{ 83 permissions: &fakePermissions{}, 84 }.Builder 85 86 exchange := exchange.NewExchange( 87 adapters, 88 nil, 89 &config.Configuration{}, 90 map[string]usersync.Syncer{}, 91 nilMetrics, 92 infos, 93 gdprPermsBuilder, 94 currency.NewRateConverter(&http.Client{}, "", time.Duration(0)), 95 empty_fetcher.EmptyFetcher{}, 96 &adscert.NilSigner{}, 97 macros.NewStringIndexBasedReplacer(), 98 nil, 99 ) 100 101 endpoint, _ := NewEndpoint( 102 fakeUUIDGenerator{}, 103 exchange, 104 paramValidator, 105 empty_fetcher.EmptyFetcher{}, 106 empty_fetcher.EmptyFetcher{}, 107 &config.Configuration{MaxRequestSize: maxSize}, 108 nilMetrics, 109 analyticsBuild.New(&config.Analytics{}), 110 map[string]string{}, 111 []byte{}, 112 nil, 113 empty_fetcher.EmptyFetcher{}, 114 hooks.EmptyPlanBuilder{}, 115 nil, 116 ) 117 118 b.ResetTimer() 119 for n := 0; n < b.N; n++ { 120 endpoint(httptest.NewRecorder(), benchmarkBuildTestRequest(), nil) 121 } 122 } 123 124 // BenchmarkValidWholeExemplary benchmarks the process that results of hitting the `openrtb2/auction` with 125 // the different JSON bid requests found in the `sample-requests/valid-whole/exemplary/` directory. As 126 // especified in said file, we expect this bid request to succeed with a 200 status code. 127 func BenchmarkValidWholeExemplary(b *testing.B) { 128 var benchInput = []string{ 129 "sample-requests/valid-whole/exemplary/all-ext.json", 130 "sample-requests/valid-whole/exemplary/interstitial-no-size.json", 131 "sample-requests/valid-whole/exemplary/prebid-test-ad.json", 132 "sample-requests/valid-whole/exemplary/simple.json", 133 "sample-requests/valid-whole/exemplary/skadn.json", 134 } 135 136 for _, testFile := range benchInput { 137 b.Run(fmt.Sprintf("input_file_%s", testFile), func(b *testing.B) { 138 b.StopTimer() 139 // Set up 140 fileData, err := os.ReadFile(testFile) 141 if err != nil { 142 b.Fatalf("unable to read file %s", testFile) 143 } 144 test, err := parseTestData(fileData, testFile) 145 if err != nil { 146 b.Fatal(err.Error()) 147 } 148 test.endpointType = OPENRTB_ENDPOINT 149 150 cfg := &config.Configuration{ 151 MaxRequestSize: maxSize, 152 BlacklistedApps: test.Config.BlacklistedApps, 153 BlacklistedAppMap: test.Config.getBlacklistedAppMap(), 154 AccountRequired: test.Config.AccountRequired, 155 } 156 157 auctionEndpointHandler, _, mockBidServers, mockCurrencyRatesServer, err := buildTestEndpoint(test, cfg) 158 if err != nil { 159 b.Fatal(err.Error()) 160 } 161 request := httptest.NewRequest("POST", "/openrtb2/auction", bytes.NewReader(test.BidRequest)) 162 recorder := httptest.NewRecorder() 163 164 // Run benchmark 165 b.ResetTimer() 166 for n := 0; n < b.N; n++ { 167 b.StartTimer() 168 auctionEndpointHandler(recorder, request, nil) //Request comes from the unmarshalled mockBidRequest 169 b.StopTimer() 170 } 171 for _, mockBidServer := range mockBidServers { 172 mockBidServer.Close() 173 } 174 mockCurrencyRatesServer.Close() 175 }) 176 } 177 }