Targeting

Targeting controls which impressions a line item — or one of its splits — is eligible to bid on. Both line item delivery and splits use the same Targeting shape: a single object keyed by attribute name, with each attribute carrying its own include/exclude flag.

type Targeting = {
  geography?:            { excluded: boolean, value: string[] };
  domain?:               { excluded: boolean, value: string[] };
  site?:                 { excluded: boolean, value: number[] };
  tagId?:                { excluded: boolean, value: string[] };
  page?:                 { excluded: boolean, value: string[] };
  device?:               { excluded: boolean, value: string[] };
  os?:                   { excluded: boolean, value: string[] };
  browser?:              { excluded: boolean, value: string[] };
  connection?:           { excluded: boolean, value: string[] };
  browserLanguage?:      { excluded: boolean, value: string[] };
  keyword?:              { excluded: boolean, value: string[] };
  firstId?:              { excluded: boolean, value: string[] };
  dayandtime?:           { excluded: boolean, value: DayAndTime[] };
  viewabilityThreshold?: { value: number };
  impData?:              DataTargeting[];
  siteAppData?:          DataTargeting[];
  userData?:             DataTargeting[];
};

type DataTargeting = {
  excluded: boolean;
  value: Record<string, string[]>;
};

All attributes use AND logic — every present attribute must pass for the line item to be eligible. Within a single attribute, excluded: false means the request value must be in value; excluded: true means it must not be.

Attribute reference

Geography & Inventory

Attribute
Matches against
Value type
Example

geography

Country, region, or city from the bid request (mixed levels supported)

string[]

['US', 'FR-IDF', 'San Francisco']

domain

site.domain (supports wildcards: *.example.com)

string[]

['example.com', '*.publisher.net']

site

imp.ext.nexx360.siteId

number[]

[2097, 3045]

tagId

imp.ext.nexx360.tagId

string[]

['yqsc1tfj']

page

site.page (exact URL match)

string[]

['https://example.com/article']

Domain matching rules

  • Only the *. prefix form is supported. Bare *, *example.com, or sub.*.com will not match anything.

  • *.example.com matches both example.com itself and any subdomain (a.example.com, a.b.example.com, …) — the apex is included, not just subdomains.

  • A leading www. is stripped from both the request's site.domain and each targeted value before comparison, so example.com and www.example.com are interchangeable.

Device & environment

Attribute
Matches against
Example

device

Device type from the bid request

['desktop', 'mobile']

os

device.os

['iOS', 'Android']

browser

Substring match against device.ua

['Chrome', 'Firefox']

connection

device.connectiontype (numeric, stringified)

['2'] (Wi-Fi)

browserLanguage

device.language (prefix matching: en matches en, en-US, …)

['en', 'fr']

Content & Identity

Attribute
Matches against
Example

keyword

site.keywords or app.keywords (comma-separated, case-insensitive)

['sport', 'news']

firstId

First-party ID from user.ext.eids (source first-id.fr)

['user-id-123']

Time & viewability

Attribute
Description

dayandtime

Day of week + hour ranges (e.g. Monday–Friday 09:00–17:00)

viewabilityThreshold

Minimum viewability percentage ({ value: 0.5 })

Data targeting

The data-targeting attributes carry an array of { excluded, value: Record<string, string[]> } entries. Each entry is a conjunction across its keys — every targeted key must have at least one matching value in the request — and entries are AND-combined.

Attribute
Reads from
Notes

impData

imp.ext.data

Per-impression data (taxonomy, segments, …)

siteAppData

site.ext.data, falling back to app.ext.data

Site/app-level data

userData

user.ext.data

User-level data (audience IDs, segments)

If the request data record is absent, an excluded: false entry fails (cannot match) and an excluded: true entry passes (no overlap to block on).

Examples

Include specific countries

Exclude specific domains

Target mobile devices only

Combine multiple attributes (AND logic)

A line item with the following targeting bids only on impressions from France or Germany, on mobile devices, for the domain publisher.com:

Day-and-time targeting

Target weekdays during business hours (UTC):

User data targeting (user.ext.data)

userData reads request.user.ext.data, a Record<string, string[]> carrying user-level segments and audience signals (audience IDs, lifestyle categories, CRM cohorts, etc.). Each entry in the userData array is a { excluded, value: Record<string, string[]> } rule. Within a single rule, all targeted keys must have at least one of their values present in the request — AND across keys, OR within a key's values.

Bid request reference

Example 1 — single audience inclusion

Only bid when the user is in the premium audience:

Example 2 — multi-key conjunction (premium AND sports)

Both keys must match. The user above (audience: ["premium", "loyalty"], category: ["sports", "news"]) passes. A user with audience: ["premium"] but category: ["finance"] fails.

Example 3 — included + excluded coexist

Premium audience required, but block any user flagged as adult category:

The included entry requires request.user.ext.data.audience to contain "premium". The excluded entry blocks if request.user.ext.data.category contains "adult". Both rules are evaluated independently — if either fails, the line item is ineligible.

Example 4 — multi-value OR within a key

Any of gold, platinum, or diamond in the user's tier field passes:

Example 5 — split-level user data targeting

The userData shape is identical at split level. A line item can run a premium-only split and a fallback split off the same impression pool:

Behaviour when user.ext.data is missing

Rule type
Outcome

excluded: false (included)

Line item ineligible — no data record means no key can match

excluded: true (excluded)

Line item passes — no data record means nothing to block on

The reader also rejects malformed shapes (values that aren't string arrays, arrays containing non-strings) and treats them as missing data.

Site/app data targeting (site.ext.dataapp.ext.data)

siteAppData reads request.site.ext.data first; if site is absent (in-app inventory), it falls back to request.app.ext.data. The same Record<string, string[]> shape applies. This is the right place for publisher-level signals like content vertical, IAB taxonomy, brand-safety flags, or page sentiment.

Bid request reference (web)

Bid request reference (in-app)

Example 1 — vertical inclusion

Only bid on finance content (works on both web and in-app inventory thanks to the fallback):

Example 2 — IAB taxonomy + sentiment

Bid on positive-sentiment news pages with the IAB12 (News) classification:

Example 3 — brand safety exclusion

Block any inventory flagged with brand-unsafe categories:

Example 4 — combined include + exclude

Stay in finance verticals but skip pages flagged with negative sentiment:

Behaviour when both site.ext.data and app.ext.data are missing

Rule type
Outcome

excluded: false (included)

Line item ineligible

excluded: true (excluded)

Line item passes

Impression data targeting (imp.ext.data)

impData reads imp.ext.data, scoped to the specific impression slot, so different ad units on the same page can carry different targeting signals (placement type, viewability segment, refresh count, contextual keywords from the ad slot, etc.). Same Record<string, string[]> shape and same matching semantics as the other two.

Bid request reference

Example 1 — above-the-fold only

Example 2 — first impression of the slot (no refresh)

The slot's refresh counter is "0" for the initial render and increments on each refresh. Targeting only the first render avoids paying for repeated views:

Example 3 — slot context match

The publisher annotates the ad slot with contextual keywords. Bid only on slots flagged as football content:

Example 4 — combined slot rules

ATF inventory only, on first render, in sports context:

Combining all three data scopes

impData, siteAppData, and userData are independent and AND-combined when present together. They allow targeting to be scoped at the right level: publisher signals on siteAppData, slot signals on impData, audience signals on userData.

The line item bids only when the publisher is finance, the slot is above the fold, and the user is in the premium audience — every layer must pass.

circle-info

A delivery-level line item must declare at least one targeting attribute to be eligible — an empty targeting object ({}) is rejected with reason targeting:none. Splits do not have this restriction; an empty split targeting matches all impressions and relies on percentage for traffic allocation.

Last updated

Was this helpful?