/
epom.go
127 lines (107 loc) · 3.36 KB
/
epom.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
package epom
import (
"encoding/json"
"fmt"
"net/http"
"github.com/mxmCherry/openrtb/v15/openrtb2"
"github.com/prebid/prebid-server/adapters"
"github.com/prebid/prebid-server/config"
"github.com/prebid/prebid-server/errortypes"
"github.com/prebid/prebid-server/openrtb_ext"
)
type adapter struct {
endpoint string
}
// Builder builds a new instance of the Epom adapter for the given bidder with the given config.
func Builder(bidderName openrtb_ext.BidderName, config config.Adapter) (adapters.Bidder, error) {
bidder := &adapter{
endpoint: config.Endpoint,
}
return bidder, nil
}
func (a *adapter) MakeRequests(request *openrtb2.BidRequest, reqInfo *adapters.ExtraRequestInfo) (requests []*adapters.RequestData, errors []error) {
rq, errs := a.makeRequest(request)
if len(errs) > 0 {
return nil, errs
}
if rq != nil {
requests = append(requests, rq)
}
return requests, nil
}
func (a *adapter) makeRequest(request *openrtb2.BidRequest) (*adapters.RequestData, []error) {
if request.Device == nil || request.Device.IP == "" {
return nil, []error{&errortypes.BadInput{
Message: "ipv4 address is required field",
}}
}
reqJSON, err := json.Marshal(request)
if err != nil {
return nil, []error{err}
}
headers := http.Header{}
headers.Add("Content-Type", "application/json;charset=utf-8")
headers.Add("Accept", "application/json")
return &adapters.RequestData{
Method: "POST",
Uri: a.endpoint,
Body: reqJSON,
Headers: headers,
}, nil
}
func (a *adapter) MakeBids(internalRequest *openrtb2.BidRequest, externalRequest *adapters.RequestData, response *adapters.ResponseData) (*adapters.BidderResponse, []error) {
if response.StatusCode == http.StatusNoContent {
return nil, nil
}
if response.StatusCode >= http.StatusInternalServerError {
return nil, []error{&errortypes.BadServerResponse{
Message: fmt.Sprintf("Unexpected status code: %d. Dsp server internal error", response.StatusCode),
}}
}
if response.StatusCode >= http.StatusBadRequest {
return nil, []error{&errortypes.BadInput{
Message: fmt.Sprintf("Unexpected status code: %d. Bad request to dsp", response.StatusCode),
}}
}
if response.StatusCode != http.StatusOK {
return nil, []error{&errortypes.BadServerResponse{
Message: fmt.Sprintf("Unexpected status code: %d", response.StatusCode),
}}
}
var bidResp openrtb2.BidResponse
if err := json.Unmarshal(response.Body, &bidResp); err != nil {
return nil, []error{err}
}
//additional no content check
if len(bidResp.SeatBid) == 0 || len(bidResp.SeatBid[0].Bid) == 0 {
return nil, []error{&errortypes.Warning{
Message: "No bids in response",
}}
}
bidResponse := adapters.NewBidderResponseWithBidsCapacity(len(bidResp.SeatBid[0].Bid))
var errs []error
for _, seatBid := range bidResp.SeatBid {
for _, bid := range seatBid.Bid {
b := &adapters.TypedBid{
Bid: &bid,
BidType: getMediaTypeForImp(bid.ImpID, internalRequest.Imp),
}
bidResponse.Bids = append(bidResponse.Bids, b)
}
}
return bidResponse, errs
}
func getMediaTypeForImp(impID string, imps []openrtb2.Imp) openrtb_ext.BidType {
for _, imp := range imps {
if imp.ID == impID {
if imp.Banner != nil {
return openrtb_ext.BidTypeBanner
} else if imp.Video != nil {
return openrtb_ext.BidTypeVideo
} else if imp.Native != nil {
return openrtb_ext.BidTypeNative
}
}
}
return openrtb_ext.BidTypeBanner
}