| Filename | Latest commit message | Latest commit date |
|---|---|---|
|
|
||
| .. | ||
| ceiling_counts_presented.m3u8 | ||
| cross_media_attested.m3u8 | ||
| README.md | ||
| vectors.json | ||
| video_rule.m3u8 | ||
live-conformance/presentation — ad presentation
The corpus of extensions/ad-presentation.md §12: rooms
of live-ads breaks under ad policies of version 2 that require
presentation claims; each viewer's break-form wai.video.ssai receipt, its session derived
from the viewer's session key; the WPC1 claims the viewers' players signed, good ones and a
control of each check; the creatives and the attestation issuer a verifier holds; what a
verifier states of them; and each accepted room's HLS tags, byte for byte.
Presentation equivalence. For each vector, a conforming verifier given its descriptor,
grants, key_log, chains, policy, pt0_ms, receipts, pods and claims, and the
corpus's creatives and issuers (§9.1), reaches the outcome the vector states, with
everything live-ads §9.4 states (see ../ads/README.md) and, for an
accepted room under a policy that requires claims (§9.4):
receipt_facts, each receipt'spresented_spend_microsbeside itsspend_micros, and itsimpressions, eachslot, the index of its ownclaimamong the claims ornull, and itsverdict:presentedor the reason it does not count;claim_facts, each claim in the order given: itsdigest(nullwhen it does not read), itsverdict, thereceiptandslotit names (from §9.2 step 3 on), and, for an impression's own claim, thequartileit reaches, itsrun_msand itsviewable_ms;spend_micros, the presented spend of every receipt together.
claim_about says what each claim is, and is not checked. A verifier that reaches another
outcome, reason, place, verdict, fact, spend or tag byte does not conform.
The corpus also carries rfc9578_a2_vector1: the pkI, TokenChallenge and token of RFC 9578
Appendix A.2's first test vector, as printed there. A conforming verifier verifies that token under
that key before it reads any token of the corpus.
Provenance. Generated here: wai_ad_presentation_vectors gen writes every file from rooms
authored in code, from fixed seeds, as ../ads/ is written. Each session key is SHA-256 of
wai:ad-presentation/corpus/player, a zero byte and its number (players lists their public
keys); each media object's content hash SHA-256 of a fixed label and two numbers; each token's
nonce SHA-256, and its salt SHA-384, of a fixed label and its number. The issuer's key is the
test key RFC 9578 Appendix A.2 publishes; the generator signs the tokens with it. Ed25519 and
RSASSA-PSS over a given salt are deterministic, so every file is the same bytes on every
machine. The generator asserts that RFC 9578's token verifies, that each vector reaches the
outcome and each claim the verdict it was written to have, and that the corpus gives every
reason of §11, before it writes. No recorded data.
Layout
vectors.json:rfc9578_a2_vector1;creatives, each itsobjects(content_hash,duration_ms);issuers, each itsname,token_typeandkeys(DER SubjectPublicKeyInfo, hexadecimal);players(informative); andvectors.NAME.m3u8: the HLS tags of each accepted room.
The rooms, each built as ../ads/'s are (a producer, a viewer and the decider, whose grant
carries the ad budget):
video_rule: a 30 s mid-roll under the video rule, five viewers each filled with ad-x (15 s) and ad-y (15 s). Presented: viewer 1's two (one partly out of view, with 3 s at 60%), viewer 3's ad-x, and viewer 7's ad-y measured over the player's area. Controls:claim_not_viewable(40% of the pixels; two runs of 1.5 s broken by a pause; a television assumption the video rule does not admit),claim_duplicate,claim_key_unbound,claim_asset_mismatch,claim_quartile_mismatch,bad_signature(its impression thenclaim_absent),claim_malformed(a signed claim that skips with no resumption stated, and a truncated claim), andclaim_no_decision.cross_media_attested: an out and its in under the cross-media rule, an audible run and an attestation of type 0x0002 fromissuer.example. Presented: viewer 11's ad-x and viewer 14's two. Controls:attestation_absent,attestation_invalid(another impression's token; an altered authenticator) andclaim_not_viewable(muted; 90% of the pixels).ceiling_counts_presented: a budget of 1 minor unit and two receipts each billing 600 000 millionths; one has a claim, so the presented spend is within the ceiling: accepted.ceiling_exceeded_by_presented: the same, both with claims:funds_exceeded.policy_attestation_without_claim:ad_policy_malformed.
Running
cd ../../wai-rs
cargo run --no-default-features --features live_ads --bin wai_ad_presentation_vectors -- verify ../live-conformance/presentation
cargo run --no-default-features --features live_ads --bin wai_ad_presentation_vectors -- gen ../live-conformance/presentation # regenerate
cargo test --no-default-features --features live_ads --test ad_presentation
cd ../live-conformance
python3 -I ad_presentation_verify.py presentation
wai_ad_presentation_vectors verify and tests/ad_presentation.rs require every file to
regenerate byte for byte, no other file but this one to be there, and wai-rs to give every
case its outcome; the test also requires §11 to list exactly the reasons the reference reports.
ad_presentation_verify.py is the second implementation, written from the extension's text and
sharing no code with wai-rs: it verifies each room, policy and receipt with
live_ads_verify.py, reads and judges every claim itself, verifies RSASSA-PSS with an
implementation of its own, reads §11 from the extension, requires every reason to appear, then
mutates copies of the corpus, one defect each, each of which must fail, and drops each of its
own checks in turn, each weakened verifier of which the corpus must catch. The browser
client's reference producer (joule-moq-web/web/ads/presentation.test.mjs) requires
video_rule's first claim from an observation sequence. Pass = an exit status of 0 from each.