adzerk / adzerk-ios-sdk

Access Adzerk's ad serving APIs via iOS
https://www.adzerk.com
Other
9 stars 5 forks source link

Support additional key/value params on each Placement as well as on the Ad Request #19

Closed karnowski closed 3 years ago

karnowski commented 4 years ago

Background

Adzerk has many optional parameters on both the ad request and on each placement inside the ad request. They all have a string key but may have arrays, string, numeric, or boolean values. They may also contain a nested object that contains its own key/value pairs.

Here's a (non-exhaustive) list of request fields: intendedLatitude, intendedLongitude, includeMatchedPoints, parallel, etc.; and here are some example placement fields: overrides, contentKeys, proportionality, ecpmPartition, etc.

The intent here is that Adzerk can continue to add new keys at both the ad request and placement level without requiring iOS developers to upgrade to a new SDK version.

Acceptance Criteria

Tech Notes

Note the iOS SDK already supports additional options at the ad request level, but the data structure has a confusing name of AZPlacementRequestOption. It is not, in fact, per Placement but only at the request level today. However, it looks like the same data structure could be used on both the placement and request level? We'd just need a n+1 of them, where n is the number of placements and the +1 is for the request.

subdigital commented 4 years ago

I believe this is now addressed by #25

A quick example:

        let placement = Placements.custom(divName: "div1", adTypes: [5])
        placement.adId = 1
        placement.campaignId = 1
        placement.flightId = 1
        placement.eventIds = [123]

        // dynamic options for the placement
        placement.additionalOptions = ["key": .string("val")]

        var options = placement.options()
        options.flightViewTimes = ["1234": [1512512, 1241212]]
        options.consent = .init(gdpr: true)
        options.blockedCreatives = [1,2,3]

        // options for the overall request
        options.keywords = ["cheese", "apples", "wine"]

The additionalOptions has a type of [String: AnyCodable]. AnyCodable is our own Codable type that gives us the flexibility to put in different structures like this:

[
    "likes": .dictionary([
        "TedLasso": .integer(25)
     ])
]

This is type safe and produces JSON like this:

{
    "likes": {
        "TedLasso": 25
    }
} 

Can you confirm this is meets the criteria?