Skip to content

Commit 5011754

Browse files
marki1anosulzhenko
andauthored
Test: Bid rounding (#3903)
Co-authored-by: osulzhenko <osulzhenko@magnite.com>
1 parent 83f53df commit 5011754

File tree

6 files changed

+159
-4
lines changed

6 files changed

+159
-4
lines changed

src/test/groovy/org/prebid/server/functional/model/config/AccountAuctionConfig.groovy

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ import com.fasterxml.jackson.databind.annotation.JsonNaming
66
import groovy.transform.ToString
77
import org.prebid.server.functional.model.bidder.BidderName
88
import org.prebid.server.functional.model.request.auction.BidAdjustment
9+
import org.prebid.server.functional.model.request.auction.BidRounding
910
import org.prebid.server.functional.model.request.auction.PaaFormat
1011
import org.prebid.server.functional.model.request.auction.Targeting
1112
import org.prebid.server.functional.model.response.auction.MediaType
@@ -31,6 +32,7 @@ class AccountAuctionConfig {
3132
PrivacySandbox privacySandbox
3233
@JsonProperty("bidadjustments")
3334
BidAdjustment bidAdjustments
35+
BidRounding bidRounding
3436

3537
@JsonProperty("price_granularity")
3638
PriceGranularityType priceGranularitySnakeCase
@@ -48,4 +50,6 @@ class AccountAuctionConfig {
4850
AccountBidValidationConfig bidValidationsSnakeCase
4951
@JsonProperty("price_floors")
5052
AccountPriceFloorsConfig priceFloorsSnakeCase
53+
@JsonProperty("bid_rounding")
54+
BidRounding bidRoundingSnakeCase
5155
}
Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
package org.prebid.server.functional.model.request.auction
2+
3+
import com.fasterxml.jackson.annotation.JsonValue
4+
5+
enum BidRounding {
6+
7+
UP("up"),
8+
DOWN("down"),
9+
TRUE("true"),
10+
TIME_SPLIT("timesplit"),
11+
UNKNOWN("unknown"),
12+
13+
private String value
14+
15+
BidRounding(String value) {
16+
this.value = value
17+
}
18+
19+
@Override
20+
@JsonValue
21+
String toString() {
22+
return value
23+
}
24+
}

src/test/groovy/org/prebid/server/functional/tests/AmpSpec.groovy

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -86,7 +86,7 @@ class AmpSpec extends BaseSpec {
8686

8787
then: "Response should contain information from stored response"
8888
def price = storedAuctionResponse.bid[0].price
89-
assert response.targeting["hb_pb"] == getRoundedTargetingValueWithDefaultPrecision(price)
89+
assert response.targeting["hb_pb"] == getRoundedTargetingValueWithDownPrecision(price)
9090
assert response.targeting["hb_size"] == "${storedAuctionResponse.bid[0].weight}x${storedAuctionResponse.bid[0].height}"
9191

9292
and: "PBS not send request to bidder"

src/test/groovy/org/prebid/server/functional/tests/BaseSpec.groovy

Lines changed: 18 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,11 @@ import org.prebid.server.functional.util.ObjectMapperWrapper
1919
import org.prebid.server.functional.util.PBSUtils
2020
import spock.lang.Specification
2121

22+
import java.math.RoundingMode
23+
2224
import static java.math.RoundingMode.DOWN
25+
import static java.math.RoundingMode.HALF_UP
26+
import static java.math.RoundingMode.UP
2327
import static org.prebid.server.functional.testcontainers.Dependencies.networkServiceContainer
2428
import static org.prebid.server.functional.util.SystemProperties.DEFAULT_TIMEOUT
2529

@@ -80,8 +84,16 @@ abstract class BaseSpec extends Specification implements ObjectMapperWrapper {
8084
logs.findAll { it.contains(text) }
8185
}
8286

83-
protected static String getRoundedTargetingValueWithDefaultPrecision(BigDecimal value) {
84-
"${value.setScale(DEFAULT_TARGETING_PRECISION, DOWN)}0"
87+
protected static String getRoundedTargetingValueWithDownPrecision(BigDecimal value) {
88+
roundWithDefaultPrecisionAndRoundingType(value, DOWN)
89+
}
90+
91+
protected static String getRoundedTargetingValueWithHalfUpPrecision(BigDecimal value) {
92+
roundWithDefaultPrecisionAndRoundingType(value, HALF_UP)
93+
}
94+
95+
protected static String getRoundedTargetingValueWithUpPrecision(BigDecimal value) {
96+
roundWithDefaultPrecisionAndRoundingType(value, UP)
8597
}
8698

8799
protected static Map<String, List<BidderRequest>> getRequests(BidResponse bidResponse) {
@@ -100,4 +112,8 @@ abstract class BaseSpec extends Specification implements ObjectMapperWrapper {
100112
List<BidderCall> bidderCalls) {
101113
[(bidderName): bidderCalls.collect { bidderCall -> decode(bidderCall.requestBody as String, BidderRequest) }]
102114
}
115+
116+
private static GString roundWithDefaultPrecisionAndRoundingType(BigDecimal value, RoundingMode roundingMode) {
117+
"${value.setScale(DEFAULT_TARGETING_PRECISION, roundingMode)}0"
118+
}
103119
}
Lines changed: 111 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,111 @@
1+
package org.prebid.server.functional.tests
2+
3+
import org.prebid.server.functional.model.config.AccountAuctionConfig
4+
import org.prebid.server.functional.model.config.AccountConfig
5+
import org.prebid.server.functional.model.db.Account
6+
import org.prebid.server.functional.model.request.auction.BidRequest
7+
import org.prebid.server.functional.model.response.auction.BidResponse
8+
import org.prebid.server.functional.util.PBSUtils
9+
10+
import static org.prebid.server.functional.model.AccountStatus.ACTIVE
11+
import static org.prebid.server.functional.model.request.auction.BidRounding.DOWN
12+
import static org.prebid.server.functional.model.request.auction.BidRounding.TRUE
13+
import static org.prebid.server.functional.model.request.auction.BidRounding.UNKNOWN
14+
import static org.prebid.server.functional.model.request.auction.BidRounding.UP
15+
16+
class BidRoundingSpec extends BaseSpec {
17+
18+
def "PBS should round bid value to the down when account bid rounding setting is #bidRoundingValue"() {
19+
given: "Default bid request"
20+
def bidRequest = BidRequest.getDefaultBidRequest().tap {
21+
enableCache()
22+
}
23+
24+
and: "Account in the DB"
25+
def account = getAccountWithBidRounding(bidRequest.accountId, bidRoundingValue)
26+
accountDao.save(account)
27+
28+
and: "Default bid response"
29+
def bidPrice = PBSUtils.randomFloorValue
30+
def bidResponse = BidResponse.getDefaultBidResponse(bidRequest).tap {
31+
seatbid[0].bid[0].price = bidPrice
32+
}
33+
bidder.setResponse(bidRequest.id, bidResponse)
34+
35+
when: "PBS processes auction request"
36+
def response = defaultPbsService.sendAuctionRequest(bidRequest)
37+
38+
then: "Targeting hb_pb should be round"
39+
def targeting = response.seatbid[0].bid[0].ext.prebid.targeting
40+
assert targeting["hb_pb"] == getRoundedTargetingValueWithDownPrecision(bidPrice)
41+
42+
where:
43+
bidRoundingValue << [new AccountAuctionConfig(bidRounding: null),
44+
new AccountAuctionConfig(bidRounding: UNKNOWN),
45+
new AccountAuctionConfig(bidRounding: DOWN),
46+
new AccountAuctionConfig(bidRoundingSnakeCase: DOWN)]
47+
}
48+
49+
def "PBS should round bid value to the up when account bid rounding setting is #bidRoundingValue"() {
50+
given: "Default bid request"
51+
def bidRequest = BidRequest.getDefaultBidRequest().tap {
52+
enableCache()
53+
}
54+
55+
and: "Account in the DB"
56+
def account = getAccountWithBidRounding(bidRequest.accountId, bidRoundingValue)
57+
accountDao.save(account)
58+
59+
and: "Default bid response"
60+
def bidPrice = PBSUtils.getRandomFloorValue()
61+
def bidResponse = BidResponse.getDefaultBidResponse(bidRequest).tap {
62+
seatbid[0].bid[0].price = bidPrice
63+
}
64+
bidder.setResponse(bidRequest.id, bidResponse)
65+
66+
when: "PBS processes auction request"
67+
def response = defaultPbsService.sendAuctionRequest(bidRequest)
68+
69+
then: "Targeting hb_pb should be round"
70+
def targeting = response.seatbid[0].bid[0].ext.prebid.targeting
71+
assert targeting["hb_pb"] == getRoundedTargetingValueWithUpPrecision(bidPrice)
72+
73+
where:
74+
bidRoundingValue << [new AccountAuctionConfig(bidRounding: UP),
75+
new AccountAuctionConfig(bidRoundingSnakeCase: UP)]
76+
}
77+
78+
def "PBS should round bid value to the up or down when account bid rounding setting is #bidRoundingValue"() {
79+
given: "Default bid request"
80+
def bidRequest = BidRequest.getDefaultBidRequest().tap {
81+
enableCache()
82+
}
83+
84+
and: "Account in the DB"
85+
def account = getAccountWithBidRounding(bidRequest.accountId, bidRoundingValue)
86+
accountDao.save(account)
87+
88+
and: "Default bid response"
89+
def bidPrice = PBSUtils.getRandomFloorValue()
90+
def bidResponse = BidResponse.getDefaultBidResponse(bidRequest).tap {
91+
seatbid[0].bid[0].price = bidPrice
92+
}
93+
bidder.setResponse(bidRequest.id, bidResponse)
94+
95+
when: "PBS processes auction request"
96+
def response = defaultPbsService.sendAuctionRequest(bidRequest)
97+
98+
then: "Targeting hb_pb should be round"
99+
def targeting = response.seatbid[0].bid[0].ext.prebid.targeting
100+
assert targeting["hb_pb"] == getRoundedTargetingValueWithHalfUpPrecision(bidPrice)
101+
102+
where:
103+
bidRoundingValue << [new AccountAuctionConfig(bidRounding: TRUE),
104+
new AccountAuctionConfig(bidRoundingSnakeCase: TRUE)]
105+
}
106+
107+
private static final Account getAccountWithBidRounding(String accountId, AccountAuctionConfig accountAuctionConfig) {
108+
def accountConfig = new AccountConfig(status: ACTIVE, auction: accountAuctionConfig)
109+
new Account(uuid: accountId, config: accountConfig)
110+
}
111+
}

src/test/groovy/org/prebid/server/functional/tests/pricefloors/PriceFloorsEnforcementSpec.groovy

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -77,7 +77,7 @@ class PriceFloorsEnforcementSpec extends PriceFloorsBaseSpec {
7777
def response = floorsPbsService.sendAmpRequest(ampRequest)
7878

7979
then: "PBS should suppress bids lower than floorRuleValue"
80-
def bidPrice = getRoundedTargetingValueWithDefaultPrecision(floorValue)
80+
def bidPrice = getRoundedTargetingValueWithDownPrecision(floorValue)
8181
verifyAll(response) {
8282
targeting["hb_pb_generic"] == bidPrice
8383
targeting["hb_pb"] == bidPrice

0 commit comments

Comments
 (0)