מדריך למפתחים בנושא Protected Audience API

בהמשך לקריאה על ארגז החול לפרטיות ב-Android תיעוד, השתמשו בלחצן תצוגה מקדימה למפתחים או בטא כדי לבחור בגרסת התוכנה שאיתה אתם עובדים, כי ההוראות עשויות להשתנות.


שליחת משוב

Protected Audience API ב-Android (לשעבר FLEDGE) כולל Custom Audience API ו-Ad Selection API. פלטפורמות ומפרסמים של טכנולוגיות פרסום יכול להשתמש בממשקי ה-API האלה כדי להציג מודעות מותאמות אישית על סמך אינטראקציות קודמות עם האפליקציה, מגבילה את השיתוף של המזהים בין אפליקציות ומגבילה את השיתוף של כל אפליקציה של משתמש על האינטראקציה עם צדדים שלישיים.

Custom Audience API מתמקד ב'קהל בהתאמה אישית' הפשטה, שמייצגת קבוצה של משתמשים עם כוונות משותפות. מפרסם יכול לרשום משתמש עם קהל מותאם אישית ולשייך מודעות רלוונטיות איתו. המידע הזה מאוחסן באופן מקומי ויכול לשמש כדי ליידע את המפרסם הצעות מחיר, סינון מודעות והצגת מודעות.

Ad Selection API מספקת מסגרת שמאפשרת למספר מפתחים: להפעיל מכרז מקומי עבור קהל מותאם אישית. כדי לעשות את זה, מביא בחשבון מודעות רלוונטיות שמשויכות לקהל המותאם אישית וביצועים עיבוד נוסף של מודעות שפלטפורמת פרסום דיגיטלי מחזירה למכשיר.

פלטפורמות פרסום דיגיטלי יכולות לשלב את ממשקי ה-API האלה כדי להטמיע רימרקטינג שומרת על פרטיות המשתמשים. תמיכה בתרחישים נוספים לדוגמה, כולל התקנת אפליקציה של מודעות מתוכננות להפצות עתידיות. מידע נוסף על Protected Audience API API ב-Android בהצעה לעיצוב.

במדריך הזה מוסבר איך לעבוד עם Protected Audience API ב-Android כדי לבצע את הפעולות הבאות:

  1. ניהול קהלים בהתאמה אישית
  2. הגדרה והפעלה של בחירת מודעות במכשיר
  3. דיווח על חשיפות של מודעות

לפני שמתחילים

לפני שמתחילים, צריך לבצע את הפעולות הבאות:

  1. מגדירים את סביבת הפיתוח לארגז החול לפרטיות ב-Android.
  2. מתקינים תמונת מערכת במכשיר נתמך או מגדירים אמולטור שכולל תמיכה בארגז החול לפרטיות ב-Android.
  3. בטרמינל, מפעילים גישה ל-Protected Audience API (מושבת) כברירת מחדל) באמצעות פקודת adb הבאה.

      adb shell device_config put adservices ppapi_app_allow_list \"*\"
    
  4. צריך לכלול הרשאת ACCESS_ADSERVICES_CUSTOM_AUDIENCE באפליקציה מניפסט:

      <uses-permission android:name="android.permission.ACCESS_ADSERVICES_CUSTOM_AUDIENCE" />
    
  5. להפנות להגדרה של שירותי מודעות ברכיב <application> של במניפסט:

      <property android:name="android.adservices.AD_SERVICES_CONFIG"
                android:resource="@xml/ad_services_config" />
    
  6. צריך לציין את משאב ה-XML של שירותי המודעות שיש אליו הפניה במניפסט, למשל res/xml/ad_services_config.xml מידע נוסף על הרשאות לשירותי מודעות ובקרת גישה ל-SDK.

      <ad-services-config>
        <custom-audiences allowAllToAccess="true" />
      </ad-services-config>
    
  7. כברירת מחדל, Ad Selection API אוכפת מגבלות בניצול המקסימלי של הזיכרון שמדווחים על מכרזים או על חשיפות שהסקריפט יכול להקצות. לתכונה 'הגבלת זיכרון' נדרשת גרסת WebView 105.0.5195.58 ומעלה. הפלטפורמה אוכפת בדיקת גרסאות וקוראת ל- ממשקי ה-API של selectAds ושל reportImpression ייכשלו. לא מרוצה. יש שתי אפשרויות להגדיר:

    • אפשרות 1: מריצים את פקודת adb הבאה כדי להשבית את הבדיקה:

      adb device_config put fledge_js_isolate_enforce_max_heap_size false
      
    • אפשרות 2: מתקינים את WebView בטא מחנות Google Play. חובה להיות שווה לגרסה שצוינה למעלה או גבוהה ממנה.

הצטרפות לקהל בהתאמה אישית

קהל בהתאמה אישית מייצג קבוצה של משתמשים עם כוונות נפוצות או תחומי עניין, כפי שנקבע על ידי האפליקציה של המפרסם. אפליקציה או SDK עשויים להשתמש בהתאמה אישית כדי לציין קהל מסוים, כמו מישהו שהשאיר פריטים בעגלת קניות. כדי ליצור קהל מותאם אישית או להצטרף אליו באופן אסינכרוני, מבצעים את הפעולות הבאות: הבאים:

  1. מאתחלים את האובייקט CustomAudienceManager.
  2. יוצרים אובייקט CustomAudience על ידי ציון פרמטרים מרכזיים כמו החבילה של הקונה ושם רלוונטי. לאחר מכן מאתחלים את האובייקט JoinCustomAudienceRequest עם הסמל CustomAudience לאובייקט.
  3. קוראים לפונקציה joinCustomAudience() האסינכרונית עם אובייקט JoinCustomAudienceRequest ורלוונטי Executor וגם OutcomeReceiver אובייקטים.

Kotlin

val customAudienceManager: CustomAudienceManager =
    context.getSystemService(CustomAudienceManager::class.java)

// Initialize a custom audience.
val audience = CustomAudience.Builder()
    .setBuyer(buyer)
    .setName(name)
    ...
    .build()

// Initialize a custom audience request.
val joinCustomAudienceRequest: JoinCustomAudienceRequest =
    JoinCustomAudienceRequest.Builder().setCustomAudience(audience).build()

// Request to join a custom audience.
customAudienceManager.joinCustomAudience(joinCustomAudienceRequest,
    executor,
    outcomeReceiver)

Java

CustomAudienceManager customAudienceManager =
    context.getSystemService(CustomAudienceManager.class);

// Initialize a custom audience.
CustomAudience audience = new CustomAudience.Builder()
    .setBuyer(buyer)
    .setName(name)
    ...
    .build();

// Initialize a custom audience request.
JoinCustomAudienceRequest joinCustomAudienceRequest =
    new JoinCustomAudienceRequest.Builder().setCustomAudience(audience).build();

// Request to join a custom audience.
customAudienceManager.joinCustomAudience(joinCustomAudienceRequest,
    executor,
    outcomeReceiver);

שילוב הפרמטרים הבאים מזהה באופן ייחודי כל אחד מהם אובייקט CustomAudience במכשיר:

  • owner: שם החבילה של אפליקציית הבעלים. מוגדר במרומז שם החבילה של אפליקציית המתקשר/ת.
  • buyer: מזהה של רשת המודעות של הקונה שמנהלת את המודעות של המודעה המותאמת אישית הזו הקהל.
  • name: שם או מזהה שרירותיים של הקהל בהתאמה אישית.

קריאה חוזרת אל joinCustomAudience() באמצעות מופע אחר של CustomAudience מעדכן את CustomAudience הקיים עם תואמים לפרמטרים owner, buyer ו-name. כדי לשמור על הפרטיות, התוצאה של ה-API לא מבחינה בין 'יצירה' ו'עדכון'.

בנוסף, צריך ליצור את CustomAudience עם הפרטים הנדרשים האלה :

פרמטרים אופציונליים לאובייקט CustomAudience יכולים לכלול:

  • זמן הפעלה: קהל בהתאמה אישית יכול להשתתף רק בבחירת מודעות ועדכונים יומיים אחרי שעת ההפעלה. האפשרות הזו יכולה לעזור לעורר עניין משתמשים שאינם פעילים באפליקציה, לדוגמה.
  • מועד תפוגה: מועד עתידי שאחריו הקהל בהתאמה אישית הוסר מהמכשיר.
  • אותות לבידינג של משתמשים: מחרוזת JSON שמכילה אותות של משתמשים, כמו המיקום המועדף על המשתמש, ש-JavaScript של הלוגיקה של הקונה לבידינג כדי ליצור הצעות מחיר בתהליך בחירת המודעות. הפורמט הזה עוזר לשפר את טכנולוגיות הפרסום פלטפורמות עושים שימוש חוזר בקוד בפלטפורמות שונות ומקלות על השימוש ב-JavaScript למשימות ספציפיות.
  • נתוני בידינג מהימנים: כתובת URL מסוג HTTPS ורשימת מחרוזות שנעשה בהן שימוש במהלך תהליך לבחירת מודעות, שמאחזר אותות לבידינג ממפתח/ערך מהימן לאחר השיפור.
  • מודעות: רשימה של אובייקטים ב-AdData שתואמים למודעות להשתתף בבחירת מודעות. כל אובייקט AdData מורכב מ:
    • כתובת URL לעיבוד: כתובת URL מסוג HTTPS שאליה נשלחת שאילתה להצגת המודעה הסופית.
    • מטא-נתונים: אובייקט JSON שעבר סריאליזציה למחרוזת שמכילה מידע צריכה להתאים ללוגיקת הבידינג של הקונה במהלך תהליך בחירת המודעה.
    • מסנני מודעות: מחלקה שמכילה את כל המידע הנדרש לאפליקציה להתקין סינון מודעות ומכסת תדירות במהלך בחירת המודעות.

דוגמה לייצוג אובייקט CustomAudience:

Kotlin

// Minimal initialization of a CustomAudience object
val customAudience: CustomAudience = CustomAudience.Builder()
    .setBuyer(AdTechIdentifier.fromString("my.buyer.domain.name"))
    .setName("example-custom-audience-name")
    .setDailyUpdateUrl(Uri.parse("https://DAILY_UPDATE_URL"))
    .setBiddingLogicUrl(Uri.parse("https://BIDDING_LOGIC_URL"))
    .build()

Java

// Minimal initialization of a CustomAudience object
CustomAudience customAudience = CustomAudience.Builder()
    .setBuyer(AdTechIdentifier.fromString("my.buyer.domain.name"))
    .setName("example-custom-audience-name")
    .setDailyUpdateUrl(Uri.parse("https://DAILY_UPDATE_URL"))
    .setBiddingLogicUrl(Uri.parse("https://BIDDING_LOGIC_URL"))
    .build();

טיפול בתוצאות שלjoinCustomAudience()

השיטה האסינכרונית joinCustomAudience() משתמשת בOutcomeReceiver לאותת התוצאה של הקריאה ל-API.

  • הקריאה החוזרת (callback) של onResult() מציינת שהקהל בהתאמה אישית הצליח נוצרו או עודכנו.
  • הקריאה החוזרת (callback) של onError() מציינת שני תנאים אפשריים.

דוגמה לטיפול בתוצאה של joinCustomAudience():

Kotlin

var callback: OutcomeReceiver<Void, AdServicesException> =
    object : OutcomeReceiver<Void, AdServicesException> {
    override fun onResult(result: Void) {
        Log.i("CustomAudience", "Completed joinCustomAudience")
    }

    override fun onError(error: AdServicesException) {
        // Handle error
        Log.e("CustomAudience", "Error executing joinCustomAudience", error)
    }
};

Java

OutcomeReceiver callback = new OutcomeReceiver<Void, AdServicesException>() {
    @Override
    public void onResult(@NonNull Void result) {
        Log.i("CustomAudience", "Completed joinCustomAudience");
    }

    @Override
    public void onError(@NonNull AdServicesException error) {
        // Handle error
        Log.e("CustomAudience", "Error executing joinCustomAudience", error);
    }
};

עזיבת קהל בהתאמה אישית

אם המשתמש כבר לא עומד בקריטריונים העסקיים של התאמה אישית ספציפית קהל היעד, אפליקציה או SDK יכולים לקרוא ל-leaveCustomAudience() כדי להסיר את ההתאמה האישית לקהל מהמכשיר. כדי להסיר CustomAudience על סמך המאפיין הייחודי שלו מבצעים את הפעולות הבאות:

  1. מאתחלים את האובייקט CustomAudienceManager.
  2. הפעלת LeaveCustomAudienceRequest עם הקהל בהתאמה אישית buyer וגם name. כדי לקבל מידע נוסף על השדות האלה להזנת קלט, אפשר לקרוא "הצטרפות לקהל בהתאמה אישית".
  3. קריאה לשיטה leaveCustomAudience() האסינכרונית עם אובייקט LeaveCustomAudienceRequest ורלוונטי Executor וגם OutcomeReceiver אובייקטים.

Kotlin

val customAudienceManager: CustomAudienceManager =
    context.getSystemService(CustomAudienceManager::class.java)

// Initialize a LeaveCustomAudienceRequest
val leaveCustomAudienceRequest: LeaveCustomAudienceRequest =
    LeaveCustomAudienceRequest.Builder()
        .setBuyer(buyer)
        .setName(name)
        .build()

// Request to leave a custom audience
customAudienceManager.leaveCustomAudience(
    leaveCustomAudienceRequest,
    executor,
    outcomeReceiver)

Java

CustomAudienceManager customAudienceManager =
    context.getSystemService(CustomAudienceManager.class);

// Initialize a LeaveCustomAudienceRequest
LeaveCustomAudienceRequest leaveCustomAudienceRequest =
    new LeaveCustomAudienceRequest.Builder()
        .setBuyer(buyer)
        .setName(name)
        .build();

// Request to leave a custom audience
customAudienceManager.leaveCustomAudience(
    leaveCustomAudienceRequest,
    executor,
    outcomeReceiver);

בדומה לקריאה אל joinCustomAudience(), האותות של OutcomeReceiver בסיום הקריאה ל-API. כדי להגן על הפרטיות, תוצאת השגיאה לא ליצור הבחנה בין שגיאות פנימיות לארגומנטים לא חוקיים. onResult() הקריאה החוזרת (callback) מתבצעת לאחר סיום הקריאה ל-API, בין אם התקבלה התאמה או לא קהל בהתאמה אישית הוסר בהצלחה.

הפעלת בחירת מודעות

כדי להשתמש ב-Protected Audience API לבחירת מודעות, צריך להפעיל את השיטה selectAds():

  1. מאתחלים אובייקט AdSelectionManager.
  2. בונים אובייקט AdSelectionConfig.
  3. קריאה לשיטה selectAds() האסינכרונית עם אובייקט AdSelectionConfig ורלוונטי Executor וגם OutcomeReceiver אובייקטים.

Kotlin

val adSelectionManager: AdSelectionManager =
  context.getSystemService(AdSelectionManager::class.java)

// Initialize AdSelectionConfig
val adSelectionConfig: AdSelectionConfig =
  AdSelectionConfig.Builder().setSeller(seller)
    .setDecisionLogicUrl(decisionLogicUrl)
    .setCustomAudienceBuyers(customAudienceBuyers)
    .setAdSelectionSignals(adSelectionSignals)
    .setSellerSignals(sellerSignals)
    .setPerBuyerSignals(perBuyerSignals)
    .setBuyerContextualAds(
      Collections.singletonMap(
        contextualAds.getBuyer(), contextualAds
      )
    ).build()

// Run ad selection with AdSelectionConfig
adSelectionManager.selectAds(
  adSelectionConfig, executor, outcomeReceiver
)

Java

AdSelectionManager adSelectionManager =
    context.getSystemService(AdSelectionManager.class);

// Initialize AdSelectionConfig
AdSelectionConfig adSelectionConfig =
  new AdSelectionConfig.Builder()
    .setSeller(seller)
    .setDecisionLogicUrl(decisionLogicUrl)
    .setCustomAudienceBuyers(customAudienceBuyers)
    .setAdSelectionSignals(adSelectionSignals)
    .setSellerSignals(sellerSignals)
    .setPerBuyerSignals(perBuyerSignals)
    .setBuyerContextualAds(
      Collections.singletonMap(contextualAds.getBuyer(), contextualAds)
    )
    .build();

// Run ad selection with AdSelectionConfig
adSelectionManager.selectAds(adSelectionConfig, executor, outcomeReceiver);

השיטה selectAds() מחייבת קלט AdSelectionConfig, שבו צריך לציין את הפרמטרים הנדרשים הבאים:

  • בית עסק: המזהה של רשת המודעות של בית העסק שממנה מתחיל בחירת המודעה.
  • כתובת ה-URL של לוגיקת ההחלטה: כתובת URL מסוג HTTPS נשלחה עם שאילתה כדי לקבל את כתובת ה-URL של רשת המודעות של בית העסק לוגיקת JavaScript.
  • קונים של קהלים בהתאמה אישית: רשימה מלאה של מזהים לרשתות המודעות של קונים שמותרות על ידי המפיץ להשתתף בתהליך בחירת המודעות. מזהי הקונים האלה תואמים ל-CustomAudience.getBuyer() מתוך בקהלים בהתאמה אישית שמשתתפים בתוכנית.

אפשר לציין את הפרמטרים הבאים כדי שההתאמה האישית של המודעות תהיה מדויקת יותר בחירה:

  • אותות לבחירת מודעות: אובייקט JSON שעבר סריאליזציה למחרוזת, שמכיל אותות שייעשה בהם שימוש על ידי לוגיקת הבידינג של הקונה, שאוחזרה מ- CustomAudience.getBiddingLogicUrl().
  • אותות של בית עסק: אובייקט JSON שעבר סריאליזציה למחרוזת, ומכיל אותות נעשה על ידי לוגיקת ההחלטה של בית העסק המאוחזרת באמצעות JavaScript, AdSelectionConfig.getDecisionLogicUrl().
  • אותות לפי קונה: מפה של אובייקטים מסוג JSON, שעברו סריאליזציה למחרוזות, שמכיל אותות לצריכה של קונים ספציפיים JavaScript של לוגיקת בידינג אוחזרו מ-CustomAudience.getBiddingLogicUrl(), שמזוהים באמצעות שדות הקונה של קהלים בהתאמה אישית שמשתתפים.
  • מודעות לפי הקשר: אוסף של מועמדים למודעות שנאספים ישירות מקונים במהלך מכרז שמתרחש מחוץ ל-Protected Audience API. במכרז.

אחרי שבוחרים מודעה, התוצאות, הצעות המחיר והאותות נשמרים באופן פנימי לצורכי דיווח. הקריאה החוזרת של OutcomeReceiver.onResult() מחזירה AdSelectionOutcome שמכיל:

  • כתובת URL לעיבוד של המודעה הזוכה, שהתקבלה מהכתובת AdData.getRenderUrl().
  • מזהה ייחודי של בחירת מודעות למשתמש במכשיר. המזהה הזה משמש לדיווח החשיפה של המודעה.

אם לא ניתן להשלים את בחירת המודעה מסיבות כמו ארגומנטים לא חוקיים, זמנים קצובים לתפוגה או צריכת משאבים מוגזמת, קריאה חוזרת של OutcomeReceiver.onError() מספקת AdServicesException עם ההתנהגויות הבאות:

  • אם בחירת המודעה מתחילה עם ארגומנטים לא חוקיים, AdServicesException מציין IllegalArgumentException בתור סיבה.
  • כל שאר השגיאות יקבלו AdServicesException עם IllegalStateException הוא הגורם לבעיה.

מודעות לפי הקשר

Protected Audience API יכול לשלב מודעות לפי הקשר במכרז מוגן. יש לבחור מודעות לפי הקשר בשרת הפרסום הדיגיטלי ולהחזיר אותן המכשיר מחוץ לממשקי ה-API של Protected Audience API. לאחר מכן ניתן לכלול מודעות לפי הקשר במכרז באמצעות AdSelectionConfig, שבשלב שבו הן פועלות זהות לאלה של מודעות במכשיר, כולל זכאות לסינון מודעות שליליות. אחרי ש המכרז של Protected Audience הושלם. עליך להפעיל reportImpression() קריאה לפעולה זו מפעילה את reportWin() במודעה ההקשרית הזוכה, זהה לדפוס של דיווח על חשיפות, כדי לקבל את המודעה הזוכה במכשיר. כל מודעה לפי הקשר זקוקה לקונה, להצעת מחיר, לקישור ללוגיקת דיווח, לעבד את כתובת האתר ואת המטא-נתונים של המודעות.

כדי לפרוס מודעות לפי הקשר באפליקציה, אפליקציית היעד צריכה ליצור אובייקט ContextualAds:

Kotlin

val contextualAds: ContextualAds =
  Builder().setBuyer(AdTechIdentifier.fromString(mBiddingLogicUri.getHost()))
    //Pass in your valid app install ads
    .setDecisionLogicUri(mContextualLogicUri)
    .setAdsWithBid(appInstallAd)
    .build()

Java

ContextualAds contextualAds = new ContextualAds.Builder()
  .setBuyer(AdTechIdentifier.fromString(mBiddingLogicUri.getHost()))
  .setDecisionLogicUri(mContextualLogicUri)
  //Pass in your valid app install ads
  .setAdsWithBid(appInstallAd)
  .build();

לאחר מכן ניתן להעביר את אובייקט ContextualAds שמתקבל במהלך היצירה AdSelectionConfig:

Kotlin

// Create a new ad
val noFilterAd: AdData = Builder()
  .setMetadata(JSONObject().toString())
  .setRenderUri(Uri.parse(baseUri + NO_FILTER_RENDER_SUFFIX))
  .build()
val noFilterAdWithBid = AdWithBid(noFilterAd, NO_FILTER_BID)
contextualAds.getAdsWithBid().add(noFilterAdWithBid)

Java

// Create a new ad
AdData noFilterAd = new AdData.Builder()
  .setMetadata(new JSONObject().toString())
  .setRenderUri(Uri.parse(baseUri + NO_FILTER_RENDER_SUFFIX))
  .build();
AdWithBid noFilterAdWithBid = new AdWithBid(noFilterAd, NO_FILTER_BID);
contextualAds.getAdsWithBid().add(noFilterAdWithBid);

סינון מודעות להתקנת אפליקציה

סינון מודעות להתקנת אפליקציות עוזר לסנן מודעות התקנה שמוצגות לאפליקציות שכבר מותקנים במכשיר.

השלב הראשון בתהליך הזה הוא להגדיר לאילו מפרסמים יש את היכולת כדי לסנן לפי החבילה המותקנת. הפעולה הזו צריכה להתבצע באפליקציה הרצויה כדי לטרגט באמצעות מודעה.

Kotlin

//Create a request for setting the app install advertisers
val adtech = AdTechIdentifier.fromString("your.enrolled.uri")
val adtechSet = setOf(adtech)
val request = SetAppInstallAdvertisersRequest(adtechSet)

//Set the app install advertisers in the ad selection manager
mAdSelectionManager.setAppInstallAdvertisers(
  request,
  mExecutor,
  object : OutcomeReceiver<Any?, Exception?>() {
    fun onResult(@NonNull ignoredResult: Any?) {
      Log.v("[your tag]", "Updated app install advertisers")
    }

    fun onError(@NonNull error: Exception?) {
      Log.e("[your tag]", "Failed to update app install advertisers", error)
    }
  })

Java

//Create a request for setting the app install advertisers
AdTechIdentifier adtech = AdTechIdentifier.fromString("your.enrolled.uri");
Set<AdTechIdentifier> adtechSet = Collections.singleton(adtech);
SetAppInstallAdvertisersRequest request = new SetAppInstallAdvertisersRequest(adtechSet);

//Set the app install advertisers in the ad selection manager
mAdSelectionManager.setAppInstallAdvertisers(
  request,
  mExecutor,
  new OutcomeReceiver<Object, Exception>() {
    @Override
    public void onResult(@NonNull Object ignoredResult) {
      Log.v("[your tag]", "Updated app install advertisers");
    }

    @Override
    public void onError(@NonNull Exception error) {
      Log.e("[your tag]", "Failed to update app install advertisers", error);
    }
  });

לאחר שהקוד הקודם מופעל, המפרסמים שהועברו יכולים לסנן את האפליקציות המותקנות שציינתם במהלך יצירת הצעת המחיר שלהן. אם המיקום עליך להסיר את הגישה של מפרסם מסוים להתקנה של האפליקציה הזו מריצים שוב את הקוד הזה לאחר הסרת פרטי המפרסם.

השלב הבא הוא הגדרה של סינון מודעות בתוך האפליקציה של בעל התוכן הדיגיטלי. המפלגה מציג את המודעה בתוך האפליקציה של בעל האפליקציה (סביר להניח שמדובר ב-SDK בצד הספק) חייבים לאתחל את האובייקט AdFilters שלהם במידע לגבי המודעות שקשורות לאפליקציות שהם רוצים לסנן:

Kotlin

// Instantiate AdFilters object with package names.
val filters: AdFilters = Builder().setAppInstallFilters(
    Builder().setPackageNames(setOf("example.target.app")).build()
  ).build()

Java

// Instantiate AdFilters object with package names.
AdFilters filters = new AdFilters.Builder()
.setAppInstallFilters(
  new AppInstallFilters.Builder()
  .setPackageNames(Collections.singleton("example.target.app"))
  .build())
.build();

בעלי תוכן דיגיטלי בצד הביקוש יכולים גם להגדיר AdFilter למודעות שקיימות בתוך את הקהלים בהתאמה אישית שלהם.

ניתן גם להעביר את AdFilters בנקודת היצירה של AdData חדש object:

Kotlin

// Instantiate an AdData object with the AdFilters created in the
// previous example.
val appInstallAd: AdData =
  Builder().setMetadata("{ ... }") // Valid JSON string
    .setRenderUri(Uri.parse("www.example-dsp1.com/.../campaign123.html"))
    .setAdFilters(filters).build()

Java

// Instantiate an AdData object with the AdFilters created in the
// previous example.
AdData appInstallAd = new AdData.Builder()
.setMetadata("{ ... }") // Valid JSON string
.setRenderUri(Uri.parse("www.example-dsp1.com/.../campaign123.html"))
    .setAdFilters(filters)
    .build();

סינון של מכסת תדירות

סינון של מכסת תדירות מאפשר לטכנולוגיות של מודעות להגביל את מספר הפעמים שמודעה מוצגת. סינון של מכסת תדירות מפחית חשיפת יתר של מודעות ומבצע אופטימיזציה של חלופות בחירת מודעות לקמפיין מסוים.

במסנן של מכסת התדירות יש שני רכיבים עיקריים: סוג האירוע של המודעה, המפתח למונה המודעות. אלה הסוגים הזמינים של אירועי מודעות:

  • זכייה (בקרוב): אירוע של זכייה מציין שהמודעה זכתה במכרז. אירועי Win מתעדכנים באופן אוטומטי על ידי Protected Audience API ואי אפשר לקבל קריאה ישירות מהמפתח. נתוני הזכייה מוצגים רק במודעות במסגרת קהל מותאם אישית.
  • חשיפה: בנפרד מ-reportImpression, מתקשר במכשיר (SSP או MMP) משתמש ב-updateAdCounterHistogram() כדי להפעיל אירועי חשיפות בקוד שהם בוחרים. אירועי חשיפות גלויים לכל המודעות השייכות ל-DSP נתון, ואינם מוגבלים למודעות באותו קהל מותאם אישית.
  • תצוגה: האירוע מופעל על ידי המתקשר במכשיר (SSP או MMP) בנקודה את הקוד שהם בוחרים באמצעות קריאה ל-updateAdCounterHistogram(). הצגת האירועים הם גלויות לכל המודעות ששייכות ל-DSP נתון ולא מוגבלות למודעות באותו זמן קהל בהתאמה אישית.
  • קליק: האירוע מופעל על ידי המתקשר במכשיר (SSP או MMP) בנקודה את הקוד שהם בוחרים באמצעות קריאה ל-updateAdCounterHistogram(). אירועי קליקים גלויות לכל המודעות ששייכות ל-DSP נתון, ולא מוגבלות למודעות אותו קהל בהתאמה אישית.

באפליקציה של בעל התוכן הדיגיטלי, מערכת SSP או MMP שיש לה נוכחות במכשיר מפעילה מודעה אירועים. כשמתבצעת קריאה אל updateAdCounterHistogram(), המונה של תדירות סינון המכסה יגדל כך שמכרזים עתידיים יהיו מעודכנים מידע לגבי החשיפה של משתמש למודעה מסוימת. סוגי האירועים של המודעה אינם משויכות באופן מאולץ לפעולה המתאימה של המשתמש, וההנחיות ניתנות כדי לעזור של המתקשרים ליצור את מערכת האירועים שלהם. כדי להגדיל את מספר ספירות המודעות במועד אירוע, המשתמש במכשיר מספק את המזהה של בחירת המודעות שזכתה במכרז.

מפתחות למונה של מודעות הם מספרים שלמים שרירותיים וחתומים בטווח 32 ביט שמוקצים על ידי מודעת קונה והן מתאימות לקבוצה נתונה של מודעות, כפי שמוגדר ב-DSP. מאז המודעה מפתחות מונה מוגבלים רק למודעות ששייכות ל-DSP נתון. המפתחות האלה יכולים ייבחרו ללא חפיפה עם היסטוגרמות מטכנולוגיית פרסום אחרת. מונה מודעות משמשים להגדלת מזהים ספציפיים ל-DSP במודעות של DSP או קהל מותאם אישית נתון כדי לסנן מודעות ממכרזים עתידיים.

אפשר להשתמש במפתחות המונה כדי לתעדף מודעות שיש סיכוי גבוה יותר יהיו מעניינות למשתמש נתון על סמך האינטראקציות שלו עם מודעות אחרות לספק טכנולוגיית המודעות של הקונה. לדוגמה, מודעה שקיבלה רמה גבוהה של מעורבות מזכייה במכרזים של מודעות, בצפיות ובקליקים, מייצגת על הגרף. כדי להמחיש זאת עוד יותר: מודעה של מועדון גולף שמאלי עשוי לציין שהמשתמש לא ירצה לראות מכשירי יד ימניים. א' מסנן מכסת תדירות המוגדר למפתח מונה שהוקצה למודעות בצד שמאל יכול סינון מודעות של מועדונים ימניים.

כדי להשתמש במכסת תדירות במכרז, קודם צריך ליצור KeyedFrequencyCap אובייקטים כפי שמוצג בהמשך:

Kotlin

// Value used when incrementing frequency counter
val adCounterKey = 123

// Frequency cap exceeded after 2 counts
val keyedFrequencyCapForImpression: KeyedFrequencyCap = Builder(
  adCounterKey, 2, Duration.ofSeconds(10)
).build()

// Frequency cap exceeded after 1 counts
val keyedFrequencyCapForImpression: KeyedFrequencyCap = Builder(
  adCounterKey, 1, Duration.ofSeconds(10)
).build()

Java

// Value used when incrementing frequency counter
int adCounterKey = 123;

// Frequency cap exceeded after 2 counts
KeyedFrequencyCap keyedFrequencyCapForImpression =
  new KeyedFrequencyCap.Builder(
    adCounterKey, 2, Duration.ofSeconds(10)
  ).build();

// Frequency Cap exceeded after 1 counts
KeyedFrequencyCap keyedFrequencyCapForClick =
  new KeyedFrequencyCap.Builder(
    adCounterKey, 1, Duration.ofSeconds(10)
  ).build();

אחרי שיוצרים את האובייקטים KeyedFrequencyCap, אפשר להעביר אותם אובייקט AdFilters.

Kotlin

val filters: AdFilters = Builder()
  .setFrequencyCapFilters(
    Builder()
      .setKeyedFrequencyCapsForImpressionEvents(
        ImmutableObject.of(keyedFrequencyCapForImpression)
      )
      .setKeyedFrequencyCapsForClickEvents(
        ImmutableObject.of(keyedFrequencyCapForClick)
      )
  ).build()

Java

AdFilters filters = new AdFilters.Builder()
    .setFrequencyCapFilters(new FrequencyCapFilters.Builder()
        .setKeyedFrequencyCapsForImpressionEvents(
            ImmutableObject.of(keyedFrequencyCapForImpression)
        )
        .setKeyedFrequencyCapsForClickEvents(
            ImmutableObject.of(keyedFrequencyCapForClick)
        )
    ).build();

כשהאובייקט AdFilters מאוכלס במסננים של מכסת תדירות, אפשר לבחור מועברות כשקהל בהתאמה אישית נוצר:

Kotlin

// Initialize a custom audience.
val audience: CustomAudience = Builder()
  .setBuyer(buyer)
  .setName(name)
  .setAds(
    listOf(
      Builder()
        .setRenderUri(renderUri)
        .setMetadata(JSONObject().toString())
        .setAdFilters(filters)
        .setAdCounterKeys(adCounterKeys)
        .build()
    )
  ).build()

Java

// Initialize a custom audience.
CustomAudience audience = new CustomAudience.Builder()
    .setBuyer(buyer)
    .setName(name)
    .setAds(Collections.singletonList(new AdData.Builder()
        .setRenderUri(renderUri)
        .setMetadata(new JSONObject().toString())
        .setAdFilters(filters)
        .setAdCounterKeys(adCounterKeys)
        .build()))
    .build();

כשמטמיעים מסננים של מכסת תדירות בקהל בהתאמה אישית, ה-SSP יכול לאחר מכן להפעיל את אירועי הקליק, הצפייה או החשיפה הנדרשים.

Kotlin

val callerAdTech: AdTechIdentifier = mAdSelectionConfig.getSeller()

val request: UpdateAdCounterHistogramRequest = Builder(
  adSelectionId,
  FrequencyCapFilters.AD_EVENT_TYPE_CLICK,  //CLICK, VIEW, or IMPRESSION
  callerAdTech
).build()

Java

AdTechIdentifier callerAdTech = mAdSelectionConfig.getSeller();

UpdateAdCounterHistogramRequest request =
  new UpdateAdCounterHistogramRequest.Builder(
      adSelectionId,
      FrequencyCapFilters.AD_EVENT_TYPE_CLICK, //CLICK, VIEW, or IMPRESSION
      callerAdTech
).build();

מודעות שעברו את תקרת הסינון המוגדרת מראש מסוננות של המכרז. הסינון מתרחש לפני הפעלת הלוגיקה של הבידינג במכרזים במכשיר, וכשהמטען הייעודי (Payload) מייצר הכנסות של בידינג מכירה פומבית מכרזים של שירותים.ערכת הכלים הזו מאפשרת לטכנולוגיות הפרסום את הגמישות להשתמש אינטראקציות בין המשתמשים לבין המודעות בקהלים בהתאמה אישית שלהם, כדי למקד את המודעה תוך צמצום חשיפת יתר של המודעות.

סינון מודעות לפי הקשר ללא קריאות רשת

אם אין ביקוש לרימרקטינג במכשיר, אפשר להציג בחירת מודעות עבור מודעות לפי הקשר ללא שיחות רשת. עם מזהי URI מוכנים מראש ורשימה של מודעות לפי הקשר עם הצעות מחיר, הפלטפורמה יכולה לדלג על אחזור הלוגיקה של הבידינג, אותות לבידינג ואותות ניקוד. הפלטפורמה משתמשת ב-URI מוגדר מראש כדי לבחור המודעה לפי הקשר עם הצעת המחיר הגבוהה ביותר.

כדי לשפר את זמן האחזור, טכנולוגיות הפרסום יכולות להפעיל תהליך לבחירת מודעות שכולל רק מודעות לפי הקשר עם פונקציונליות של סינון מודעות ללא קריאות רשת. הדבר באמצעות שימוש במזהי URI מוכנים מראש לאותות דירוג. עיינו במאמרים נתמכים קטע בנושא שמות ותרחישים לדוגמה מראש של URI לרשימה של scoreAds בפועל.

כדי להציג בחירת מודעות ללא שיחות רשת:

  1. הגדרה של סינון מודעות
  2. יצירת מודעות לפי הקשר
  3. יוצרים אובייקט AdSelectionConfig עם הפרטים הבאים:

    1. רשימה ריקה של קונים
    2. URI מובנה מראש כדי לבחור את הצעת המחיר הגבוהה ביותר
    3. מודעות לפי הקשר
    4. URI ריק עבור אותות הציון. ה-URI הריק יכול לציין שאתם לא רוצים להשתמש באחזור האותות המהימנים לצורך חישוב הציון:
    Uri prebuiltURIScoringUri = Uri.parse("ad-selection-prebuilt://ad-selection/highest-bid-wins/?reportingUrl=your.registered.uri/reporting");
    // Initialize AdSelectionConfig
    AdSelectionConfig adSelectionConfig =
      new AdSelectionConfig.Builder()
        .setSeller(seller)
        .setDecisionLogicUri(prebuiltURIScoringUri)
        .setCustomAudienceBuyers(Collections.emptyList())
        .setAdSelectionSignals(adSelectionSignals)
        .setSellerSignals(sellerSignals)
        .setPerBuyerSignals(perBuyerSignals)
        .setBuyerContextualAds(buyerContextualAds)
        .setTrustedScoringSignalsUri(Uri.EMPTY)
        .build();
    
  4. הפעלת בחירת מודעות:

    adSelectionManager.selectAds(
        adSelectionConfig,
        executor,
        outcomeReceiver);
    

הרצת JavaScript לדיווח משלכם תוך שימוש במזהי URI מוכנים מראש

כיום, לפלטפורמה של ארגז החול לפרטיות יש רק JavaScript בסיסי לדיווח זמינה למזהי URI מוכנים מראש. אם רוצים לנהל דיווח על JavaScript תוך שימוש במזהי URI מוכנים מראש למודעה עם זמן אחזור קצר הבחירה הזו, אפשר לשנות את DecisionLogicUri בין בחירת המודעה לבין הדוחות.

  1. מפעילים את השלבים להפעלת בחירת מודעות עבור מודעות לפי הקשר באמצעות מזהי URI מוכנים מראש
  2. לפני שמפעילים את הדיווח צריך ליצור עותק של AdSelectionConfig

    adSelectionConfigWithYourReportingJS = adSelectionConfig.cloneToBuilder()
      // Replace <urlToFetchYourReportingJS> with your own URL:
      .setDecisionLogicUri(Uri.parse(<urlToFetchYourReportingJS>))
      .build();
    
  3. הפעלת דיווח על חשיפות

    // adSelectionId is from the result of the previous selectAds run
    ReportImpressionRequest request = new ReportImpressionRequest(
      adSelectionId,
      adSelectionConfigWithYourReportingJS);
    adSelectionManager.reportImpression(
      request,
      executor,
      outcomeReceiver);
    

הפעלה של רשימת הרשתות בתהליך בחירת הרשת

כדי להשתמש בתהליך בחירת הרשת ב-Waterfall, צריך להגדיר כמה ערכות SDK של צד שלישי (רשתות צד שלישי) תוזמנה על ידי רשת לבחירת רשת (Mediation) SDK של צד ראשון. תהליך בחירת הרשת ב-Waterfall הוא באותה הדרך, ללא קשר למכרז שבו התנהלה במכשיר או התנהלה בידינג ו שירותי מכרזים (B&A).

רשתות של צד שלישי

רשתות הצד השלישי צריכות לספק מתאם שמאפשר לרשת תהליך בחירת הרשת (Mediation) להפעיל את השיטות הנדרשות להפעלת מכרז:

  • הפעלת בחירת מודעות
  • דיווח על חשיפות

דוגמה למתאם רשת בתהליך בחירת הרשת:

Kotlin

class NetworkAdaptor {
    private val adSelectionManager : AdSelectionManager

    init {
        adSelectionManager = context.getSystemService(AdSelectionManager::class.java)
    }

    fun selectAds() {...}

    fun reportImpressions() {...}
}

Java

class NetworkAdaptor {
    AdSelectionManager adSelectionManager;

    public NetworkAdaptor() {
        AdSelectionManager adSelectionManager =
            context.getSystemService(AdSelectionManager.class);
    }

    public void selectAds() {...}

    public void reportImpressions() {...}
}

לכל SDK יש מנהלי שירות ולקוחות משלהם לבחירת מודעות, הטמעה של selectAds ו-reportImpressions. ספקי SDK יכולים לעיין לקטעים על הפעלת בחירת מודעות עבור מכרזים במכשיר או מודעות לקידום מלונות הסברלמכרזי מלונות. הוראות לדיווח על מודעה חשיפות (בהתאם לדיווח על חשיפות יחיד של SSP עבור דיווח.

רשת תהליך בחירת הרשת (Mediation)

בדומה לרשתות של צד שלישי, לרשתות בתהליך בחירת הרשת צריך להגדיר selectAds וגם reportImpression מוטמעים. מומלץ לעיין בקטעים בנושא הפעלת מודעה בחירה ואיך לדווח על חשיפות של מודעות, כדי לקבל מידע נוסף.

הרשתות בתהליך בחירת הרשת אחראיות להפעלת שרשרת תהליך בחירת הרשת (Mediation) ולמיקום בשרשרת לבחירת רשת. בקטע הבא מוסבר איך מגדירים מפעילים את התהליך הזה.

אחזור של שרשרת תהליך בחירת הרשת וערכי סף תחתון להצעות מחיר

הרשת לבחירת רשת אחראית לאחזור הנתונים מהאינטראקציה הישירה (First-Party) מודעות לפי הקשר, שרשרת לבחירת רשת ורשתות צד שלישי ערכי סף להצעות מחיר (צד ג'). הזה יכול לקרות בבקשה לאחזור מודעות לפי הקשר שהופעלו על ידי הגישור עמוקה מאוד, שרשרת תהליך בחירת הרשת קובעת איך לחזור על עצמן דרך הרשתות של הצד השלישי, וניתן להעביר את ערכי הסף התחתון של הצעת המחיר לתהליך המכרז בתור adSelectionSignals.

מיקום הרשת בשרשרת לבחירת רשת

ערכת SDK של תהליך בחירת הרשת יכולה למקם את עצמה בשרשרת לבחירת רשת על סמך העלות בפועל לאלף חשיפות (eCPM) שלה בזמן אמת של הצעות מחיר למודעות מאינטראקציה ישירה. ב-Protected Audience API, הצעות המחיר למודעות הן אטומות. תהליך בחירת הרשת (Mediation) ערכת ה-SDK צריכה להשתמש ב-AdSelectionFromOutcomesConfig כדי להשוות בין נתונים מאינטראקציה ישירה הצעת המחיר של המודעה לסף הצעת המחיר של הרשת הבאה של צד שלישי בשרשרת. אם הצעת המחיר מאינטראקציה ישירה היא גבוהה מהסף התחתון להצעת המחיר, המשמעות היא שערכת ה-SDK של תהליך בחירת הרשת (Mediation) נמצאת בחזית של רשת הצד השלישי הזאת.

הפעלת בחירת מודעות

כדי לאחזר אפשרות להצגת מודעות מאינטראקציה ישירה, הרשת בתהליך בחירת הרשת יכולה להפעיל במכשיר במכרז על פי השלבים המפורטים בקטע הפעלת בחירת מודעות. הפעולה הזו יוצרת מועמד למודעה מאינטראקציה ישירה, הצעת מחיר ו-AdSelectionId שנמצאים בשימוש בתהליך בחירת הרשת תהליך האימות.

יצירת AdSelectionFromresultsConfig

AdSelectionFromOutcomesConfig מאפשר לרשת בתהליך בחירת הרשת להעביר רשימה של AdSelectionIds (תוצאות ממכרזים קודמים), אותות לבחירת מודעות ו URI לאחזור JavaScript שבוחר מודעה מתוך מועמדים מרובים. הרשימה של AdSelectionIds יחד עם הצעות המחיר שלהם והאותות מועברים אל JavaScript שיכול להחזיר אחד מהערכים AdSelectionIds אם הוא גבוה מהצעת המחיר סף תחתון או כלל לא אם שרשרת בחירת הרשת אמורה להמשיך.

הרשתות בתהליך בחירת הרשת (Mediation) יוצרות AdSelectionFromOutcomesConfig באמצעות הצד השלישי AdSelectionId מהקטע הקודם, והסף התחתון להצעת המחיר לרשת הצד השלישי ואנחנו שוקלים אותם. צריך ליצור AdSelectionFromOutcomesConfig חדש לכל שלב בשרשרת לבחירת רשת.

Kotlin

fun  runSelectOutcome(
    adSelectionClient : AdSelectionClient,
    outcome1p : AdSelectionOutcome,
    network3p : NetworkAdapter) : ListenableFuture<AdSelectionOutcome?> {
    val config = AdSelectionFromOutcomesConfig.Builder()
        .setSeller(seller)
        .setAdSelectionIds(listOf(outcome1p))
        .setSelectionSignals({"bid_floor": bid_floor})
        .setSelectionLogicUri(selectionLogicUri)
        .build()
    return adSelectionClient.selectAds(config)
}

Java

public ListenableFuture<AdSelectionOutcome> runSelectOutcome(AdSelectionOutcome outcome1p,
                                              NetworkAdapter network3p) {
    AdSelectionFromOutcomesConfig config = new AdSelectionFromOutcomesConfig.Builder()
            .setSeller(seller)
            .setAdSelectionIds(Collection.singletonList(outcome1p))
            .setSelectionSignals({"bid_floor": bid_floor})
            .setSelectionLogicUri(selectionLogicUri)
            .build();

    return adSelectionClient.selectAds(config){}
}

כדי לשנות את שיטת הפעולה selectAds() ברשימת הרשתות בתהליך בחירת הרשת, צריך להגדיר קלט AdSelectionFromOutcomesConfig, כשצריך לציין בו את הדברים הבאים הפרמטרים הנדרשים:

  • בית עסק: המזהה של רשת המודעות של בית העסק שממנה מתחיל בחירת המודעה.
  • AdSelectionIds: רשימה של מקטע בודד של נתונים קודמים של selectAds() מאינטראקציה ישירה המודעה.
  • אותות לבחירת מודעות: אובייקט JSON שעבר סריאליזציה למחרוזת, שמכיל שבהם ישמשו את הלוגיקה של הבידינג של הקונים. במקרה כזה, יש לציין את הסף התחתון להצעת המחיר מאוחזר לרשת הצד השלישי הנתונה.
  • URI של לוגיקת בחירה: כתובת URL מסוג HTTPS נשלחה שאילתה במהלך בחירת המודעה כדי לאחזר את ה-JavaScript של הרשת לבחירת הרשת לבחירת המודעה הזוכה. הפרטים הנדרשים פונקציות חתימות ב-JavaScript הזה. ה-JavaScript אמור להחזיר את מודעה של צד שלישי אם הצעת המחיר גבוהה מהסף התחתון להצעת המחיר, או אם היא מחזירה null באופן אחר. כך ל-SDK של תהליך בחירת הרשת (Mediation) תהיה אפשרות לקצר את שרשרת תהליך בחירת הרשת כאשר מנצחת נמצא.

אחרי שה-AdSelectionOutcomesConfig נוצר, מפעילים את ה-method selectAds() של ברשת הצד השלישי שנמצאת ראשונה בשרשרת.

Kotlin

val adSelectionManager = context.getSystemService(AdSelectionManager::class.java)

// Initialize AdSelectionFromOutcomesConfig
AdSelectionFromOutcomesConfig adSelectionFromOutcomesConfig =
  AdSelectionFromOutcomesConfig.Builder()
    .setSeller(seller)
    .setAdSelectionIds(listof(outcome1p))
    .setSelectionSignals({"bid_floor": bid_floor})
    .setSelectionLogicUri(selectionLogicUri)
    .setAdSelectionIds(outcomeIds)
    .build()

// Run ad selection with AdSelectionConfig
adSelectionManager.selectAds(
    adSelectionFromOutcomesConfig,
    executor,
    outcomeReceiver)

Java

AdSelectionManager adSelectionManager =
    context.getSystemService(AdSelectionManager.class);

// Initialize AdSelectionFromOutcomesConfig
AdSelectionFromOutcomesConfig adSelectionFromOutcomesConfig =
        new AdSelectionFromOutcomesConfig.Builder()
            .setSeller(seller)
            .setAdSelectionIds(Collection.singletonList(outcome1p))
            .setSelectionSignals({"bid_floor": bid_floor})
            .setSelectionLogicUri(selectionLogicUri)
            .setAdSelectionIds(outcomeIds)
            .build();

// Run ad selection with AdSelectionConfig
adSelectionManager.selectAds(
    adSelectionFromOutcomesConfig,
    executor,
    outcomeReceiver);

תזמור רשימת רשתות בתהליך בחירת הרשת

זהו סדר הפעולות לביצוע תהליך בחירת הרשת (Mediation) תהליך האימות.

  1. הפעלת בחירת מודעות מאינטראקציה ישירה.
  2. איטרציה לאורך שרשרת תהליך בחירת הרשת. בכל רשת של צד שלישי:
    1. Build AdSelectionFromOutcomeConfig, כולל outcomeId מאינטראקציה ישירה וגם הסף התחתון להצעת המחיר ל-SDK של צד שלישי.
    2. קוראים לפונקציה selectAds() עם ההגדרות מהשלב הקודם.
    3. אם לא מופיעה תוצאה ריקה, מחזירים את המודעה.
    4. קוראים לשיטה selectAds() של מתאם רשת ה-SDK הנוכחי. אם התוצאה לא ריק, החזר את המודעה.
  3. אם לא נמצא מנצח ברשת, מחזירים את המודעה מאינטראקציה ישירה.

Kotlin

fun runWaterfallMediation(mediationChain : List<NetworkAdapter>)
  : Pair<AdSelectionOutcome, NetworkAdapter> {
    val outcome1p = runAdSelection()

    var outcome : AdSelectionOutcome
    for(network3p in mediationChain) {
      outcome = runSelectOutcome(outcome1p, network3p)
      if (outcome1p.hasOutcome() && outcome.hasOutcome()) {
          return Pair(outcome, this)
      }

      outcome = network3p.runAdSelection()
      if(outcome.hasOutcome()) {
          return Pair(outcome, network3p)
      }
    }
  return Pair(outcome1p, this)
}

Java

class MediationNetwork {
    AdSelectionManager adSelectionManager;

    public MediationNetwork() {
        AdSelectionManager adSelectionManager =
            context.getSystemService(AdSelectionManager.class);
    }

    public void runAdSelection() {...}

    public void reportImpressions() {...}

    public Pair<AdSelectionOutcome, NetworkAdapter> runWaterfallMediation(
            List<NetworkAdapter> mediationChain) {
        AdSelectionOutcome outcome1p = runAdSelection();

        AdSelectionOutcome outcome;
        for(NetworkAdapter network3p: mediationChain) {
            if (outcome1p.hasOutcome() &&
              (outcome = runSelectOutcome(outcome1p, network3p)).hasOutcome()) {
                return new Pair<>(outcome, this);
            }

            if((outcome = network3p.runAdSelection()).hasOutcome()) {
                return new Pair<>(outcome, network3p);
            }
        }
        return new Pair<>(outcome1p, this);
    }

    /* Runs comparison by creating an AdSelectionFromOutcomesConfig */
    public AdSelectionOutcome runSelectOutcome(AdSelectionOutcome outcome1p,
                                              NetworkAdapter network3p) { ... }
}

דיווח על חשיפות של מודעות

יש שני תהליכי דיווח על חשיפה של מודעה, בהתאם לאופן שבו המכרז מופעלת. אם אתם ספק SSP אחד שמפעיל מכרז, יש לעיין בקטע הבא. אם המיקום שבכוונתכם להטמיע את רשימת הרשתות בתהליך בחירת הרשת, צריך לפעול לפי השלבים המפורטים בקטע 'דיווח על חשיפות בתהליך בחירת הרשת ב-Waterfall'.

דיווח על חשיפות SSP יחיד

אחרי שבוחרים מודעה מנצחת מתוך תהליך העבודה של בחירת המודעות, אפשר לבצע את הפעולות הבאות: לדווח על החשיפה לפלטפורמות שמשתתפות בתוכנית בצד הקונה ובצד המוכר באמצעות השיטה AdSelectionManager.reportImpression(). איך מדווחים על מודעה חשיפה:

  1. מאתחלים אובייקט AdSelectionManager.
  2. יוצרים אובייקט ReportImpressionRequest עם המזהה של בחירת המודעות.
  3. קריאה לשיטה reportImpression() האסינכרונית עם אובייקט ReportImpressionRequest ורלוונטי Executor וגם OutcomeReceiver אובייקטים.

Java

AdSelectionManager adSelectionManager =
    context.getSystemService(AdSelectionManager.class);

// Initialize a ReportImpressionRequest
ReportImpressionRequest reportImpressionRequest =
        new ReportImpressionRequest.Builder()
                .setAdSelectionId(adSelectionId)
                .setAdSelectionConfig(adSelectionConfig)
                .build();

// Request to report the impression with the ReportImpressionRequest
adSelectionManager.reportImpression(
    reportImpressionRequest,
    executor,
    outcomeReceiver);

Kotlin

val adSelectionManager = context.getSystemService(AdSelectionManager::class.java)

// Initialize a ReportImpressionRequest
val adSelectionConfig: ReportImpressionRequest =
    ReportImpressionRequest.Builder()
        .setAdSelectionId(adSelectionId)
        .setAdSelectionConfig(adSelectionConfig)
        .build()

// Request to report the impression with the ReportImpressionRequest
adSelectionManager.reportImpression(
    reportImpressionRequest,
    executor,
    outcomeReceiver)

צריך להפעיל את ReportImpressionRequest עם הדרישות הבאות :

  • מזהה בחירת מודעות: מזהה ייחודי למשתמש במכשיר שמזהה בחירה מוצלחת של המודעה.
  • הגדרה של בחירת מודעות: אותה הגדרה ששימשה בשדה selectAds() קריאה מזוהה לפי המזהה שצוין לבחירת המודעה.

השיטה האסינכרונית reportImpression() משתמשת בOutcomeReceiver לאותת התוצאה של הקריאה ל-API.

  • הקריאה החוזרת (callback) של onResult() מציינת אם כתובות ה-URL לדיווח על חשיפות נוצרה והבקשה תוזמנה.
  • הקריאה החוזרת של onError() מציינת את התנאים האפשריים הבאים:
    • אם הקריאה מאותחלת עם ארגומנט קלט לא חוקי, AdServicesException מציין IllegalArgumentException בתור הסיבה.
    • כל שאר השגיאות יקבלו AdServicesException עם IllegalStateException הוא הגורם לבעיה.

דיווח על חשיפות בתהליך בחירת הרשת (Mediation) ב-Waterfall

ערכת ה-SDK של תהליך בחירת הרשת (Mediation) צריכה לעקוב אחרי ערכת ה-SDK הזוכה כדי להפעיל את בדיווחים. ערכות ה-SDK שמשתתפות בשרשרת לבחירת רשת צריכות לספק כדי שהמגשר יוכל להפעיל את תהליך הדיווח שלו. SDK שמשתתפים במכרז של תהליך בחירת הרשת (Mediation) יכולים לפעול לפי השלבים שמפורטים למעלה כדי להטמיע, הדוחות שלהם.

ספקי SSP יכולים להשתמש בדוגמה הזו לקוד ה-SDK של צד שלישי בתור אב טיפוס של הדרך להצטרף תהליכי בחירת הרשת:

Pair<AdSelectionOutcome, NetworkAdapter> winnerOutcomeAndNetwork =
         mediationSdk.orchestrateMediation(mediationChain);

if (winner.first.hasOutcome()) {
      winner.second.reportImpressions(winner.first.getAdSelectionId());

נקודות קצה לדיווח על חשיפות

הדוח 'ה-API של החשיפות' מנפיק בקשות מסוג HTTPS GET לנקודות קצה (endpoints) שסופקו על ידי הפלטפורמה בצד המוכר והפלטפורמה הזוכה בצד הקונה:

נקודת קצה בפלטפורמה בצד הקונה:

  • ה-API משתמש בכתובת ה-URL של הלוגיקה לבידינג שצוינה בקהל בהתאמה אישית כדי לאחזר את ה-JavaScript שסופק על ידי הקונה וכולל לוגיקה להחזרת כתובת URL לדיווח על חשיפות.
  • מפעילים את פונקציית ה-JavaScript reportWin(), שאמורה לחזור כתובת האתר לדיווח על חשיפות של הקונה.

נקודת קצה בפלטפורמה בצד המוכר:

  • משתמשים בכתובת ה-URL של לוגיקת ההחלטה שצוינה ב-AdSelectionConfig כדי לאחזר את קוד ה-JavaScript של לוגיקת ההחלטה של בית העסק.
  • מפעילים את פונקציית ה-JavaScript reportResult(), שאמורה להחזיר את כתובת האתר לדיווח על חשיפות של בית העסק.

בידינג ו דיווח על שירותי מכרזים

מכרז שמופעל על ידי בידינג לשירותי המכרז יהיו כל מידע, כולל כתובות URL שנוצרות לדיווח על אינטראקציות עם מודעות, נכללות בתגובה המוצפנת מהמכרז בצד השרת. כאשר שהתשובה מפוענחת, כתובות ה-URL המתאימות רשומות בפלטפורמה, כך הדיווח על מודעות ועל חשיפות כולל את אותם השלבים שמפורטים למעלה.

הדיווח על חשיפות במאמץ הטוב ביותר

השיטה reportImpression() נועדה להציע את ההשלמה הטובה ביותר של דיווח.

דיווח על אינטראקציות עם מודעות

Protected Audience API תומך בדיווח על אינטראקציות מפורטות יותר עבור מודעה שעברה עיבוד. האינטראקציות האלה עשויות לכלול אינטראקציות כמו זמן צפייה, קליקים, העברות עכבר, או כל מדד שימושי אחר שניתן לאסוף. התהליך לקבלת נדרשים שני שלבים. ראשית, קונים ומוכרים חייבים להירשם כדי לקבל בדוחות האלה ב-JavaScript לדיווח. לאחר מכן הלקוח יצטרך לדווח על האירועים האלה.

הרשמה לקבלת אירועי אינטראקציה

הרשמה לאירועי אינטראקציה מתרחשת בreportWin() של הקונה, פונקציות JavaScript reportResult() של המוכר באמצעות פונקציית JavaScript סופקו על ידי הפלטפורמה: registerAdBeacon. כדי להירשם לקבלת דוח אירועים, פשוט מפעילים את הפונקציה JavaScript של הפלטפורמה מתוך הדוחות JavaScript. קטע הקוד הבא משתמש ב-reportWin() של קונה, אך הוא זהה חלה על reportResult().

reportWin(
  adSelectionSignals,
  perBuyerSignals,
  signalsForBuyer,
  contextualSignals,
  customAudienceSignals) {
    ...
    // Calculate reportingUri, clickUri, viewUri, and hoverUri

    registerAdBeacon({"click": clickUri, "view": viewUri, "hover": hoverUri});

    return reportingUri;
}

אירועי אינטראקציה בדיווח

לאחר דיווח על חשיפה, לקוחות יכולים לדווח על האינטראקציות חזרה אל רשומות מנצחות בצד הקונה ובצד המוכר שנרשמו בעבר עם אמצעי תשלום אחד (AdSelectionManager.reportInteraction()). כך מדווחים על אירוע מודעה:

  1. מאתחלים אובייקט AdSelectionManager.
  2. יוצרים אובייקט ReportInteractionRequest עם המזהה של בחירת המודעות. מפתח אינטראקציה, נתוני אינטראקציה ויעד לדיווח.
  3. קריאה לשיטה reportInteraction() האסינכרונית עם האובייקט request ואובייקטים רלוונטיים של Executor ו-OutcomeReceiver.
AdSelectionManager adSelectionManager =
    context.getSystemService(AdSelectionManager.class);

// Initialize a ReportInteractionRequest
ReportInteractionRequest request =
  new ReportInteractionRequest.Builder()
    .setAdSelectionId(adSelectionId)
    .setInteractionKey("view")
    .setInteractionData("{ viewTimeInSeconds : 1 }") // Can be any string
    .setReportingDestinations(
      FLAG_REPORTING_DESTINATION_BUYER | FLAG_REPORTING_DESTINATION_SELLER
    )
    .build();

// Request to report the impression with the ReportImpressionRequest
adSelectionManager.reportInteraction(
  reportImpressionRequest,
  executor,
  outcomeReceiver);

צריך להפעיל את ReportInteractionRequest עם הדרישות הבאות :

  • מזהה בחירת מודעות: מזהה בחירת מודעה, שאוחזר מתוך מודעה שהוחזרה בעבר AdSelectionOutcome.
  • מפתח אינטראקציה: מפתח מחרוזת שמוגדר על ידי הלקוח שמתאר את הפעולה שידווחו. המזהה צריך להתאים למפתח שרשמת על ידי בית העסק, או בפונקציות ה-JavaScript של הדיווח.
  • נתוני אינטראקציה: מחרוזת שמכילה נתונים שייכללו באירוע כדי להופיע חזרה לשרתי הדיווח.
  • יעדי דיווח: מסכה קטנה שמציינת אם האירועים ידווחו לקונה, למפיץ או לשניהם. הסימונים האלה מסופקים על ידי ואת מסכת היעד הסופית ניתן ליצור באמצעות ב-AI. כדי לדווח ליעד אחד, אפשר להשתמש בדגל שסופק על-ידי ישירות בפלטפורמה. כדי לדווח ליעדים מרובים, אפשר להשתמש במאפיין הסיביות או (|) כדי לשלב ערכי דגל.

השיטה האסינכרונית reportInteraction() משתמשת בOutcomeReceiver לאותת התוצאה של הקריאה ל-API.

  • הקריאה החוזרת (callback) של onResult() מציינת שהקריאה לאינטראקציה בדוח חוקית.
  • הקריאה החוזרת של onError() מציינת את התנאים האפשריים הבאים:
    • אם השיחה מתבצעת כשהאפליקציה פועלת ברקע, הפונקציה IllegalStateException עם תיאור של הכשל מוחזרת.
    • אם יש ויסות נתונים (throttle) של הלקוח מהתקשרות אל reportInteraction(), השדה LimitExceededException הוחזר.
    • אם החבילה לא רשומה להפעלה של ממשקי ה-API לשמירה על פרטיות, השדה SecurityException() הוחזר.
    • אם האינטראקציות לדיווח על האפליקציה שונות מהאפליקציה שנקראת selectAds(), מוחזר IllegalStateException.
  • אם המשתמש לא הסכים להפעיל את ממשקי ה-API של ארגז החול לפרטיות, תתבצע קריאה תיכשל בשקט.

נקודות קצה לדיווח על אינטראקציות

ה-Reporting API מנפיק בקשות HTTPS POST לנקודות קצה (endpoints) שסופקו על ידי הפלטפורמה בצד המוכר והפלטפורמה המנצחת בצד הקונה. קהל מוגן יתאים בין מפתחות האינטראקציה למזהי ה-URI שהוצהרו ב-JavaScript לדיווח והם שולחים בקשת POST לכל נקודת קצה (endpoint) עבור כל אינטראקציה שמדווחת. סוג התוכן של הבקשה הוא טקסט פשוט שבו הגוף הוא נתוני אינטראקציה.

הדיווח על אינטראקציות עם הסיכוי הכי טוב

המטרה של reportInteraction() היא לאפשר את הפעולה הטובה ביותר דיווח באמצעות HTTP POST.

עדכון רקע יומי

כשיוצרים קהל בהתאמה אישית, האפליקציה או ה-SDK יכולים להפעיל קהל בהתאמה אישית מטא-נתונים. בנוסף, הפלטפורמה יכולה לעדכן את החלקים הבאים של מטא-נתונים של קהל עם תהליך עדכון יומי ברקע.

  • אותות לבידינג של משתמשים
  • נתוני בידינג מהימנים
  • רשימה אחת (AdData)

בתהליך הזה נשלחות שאילתות לגבי כתובת ה-URL לעדכון יומי שהוגדרה בקהל בהתאמה אישית וכתובת ה-URL עשויה להחזיר תגובת JSON.

  • תגובת JSON עשויה להכיל כל אחד משדות המטא-נתונים הנתמכים שנדרשים להם צריך להתעדכן.
  • כל שדה JSON מאומת בנפרד. הלקוח מתעלם מכל אחד לשדות שגויים, וכתוצאה מכך לא יתקבלו עדכונים לשדה המסוים הזה את התשובה.
  • תגובת HTTP ריקה או אובייקט JSON ריק "{}" לא התקבלו תוצאות ועדכוני מטא-נתונים.
  • הגודל של הודעת התשובה חייב להיות מוגבל ל-10KB.
  • כל מזהי ה-URI נדרשים להשתמש ב-HTTPS.
  • trusted_bidding_uri חייב לשתף את אותו ETLD+1 כמו הקונה.

דוגמה: תגובת JSON לעדכון יומי ברקע

{
    "user_bidding_signals" : { ... },  // Valid JSON object
    "trusted_bidding_data" : {
        "trusted_bidding_uri" : 'example-dsp1-key-value-service.com',
        "trusted_bidding_keys" : [ 'campaign123', 'campaign456', ... ]
    },
    'ads' : [
        {
            "render_uri" : 'www.example-dsp1.com/.../campaign123.html',
            'metadata' : { ... }  // Valid JSON object
        },
        {
            "render_uri" : 'www.example-dsp1.com/.../campaign456.html',
            'metadata' : { ... }  // Valid JSON object
        },
        ...
    ]
}

JavaScript לבחירת מודעות

תהליך העבודה לבחירת מודעות מתזמר את ביצוע הפעולות שסופקו על ידי הקונה JavaScript שסופק על ידי בית העסק.

JavaScript שסופק על ידי הקונה מאוחזר מכתובת ה-URL של לוגיקת הבידינג שצוינה ב קהל בהתאמה אישית. קוד ה-JavaScript שמוחזר צריך לכלול את הפונקציות הבאות:

JavaScript שסופק על ידי בית העסק מאוחזר מכתובת ה-URL של לוגיקת ההחלטות שצוינה ב- הפרמטר AdSelectionConfig ל-API לבחירת מודעות. המוחזר קוד JavaScript צריך לכלול את הפונקציות הבאות:

generateBid()

function generateBid(
  ad,
  auction_signals,
  per_buyer_signals,
  trusted_bidding_signals,
  contextual_signals,
  user_signals,
  custom_audience_bidding_signals) {
  return {'status': 0, 'ad': ad, 'bid': ad.metadata.result };
}

פרמטרים של קלט:

  • ad: אובייקט JSON בפורמט var ad = { 'render_url': url, 'metadata': json_metadata };
  • auction_signals, per_buyer_signals: אובייקטים מסוג JSON שצוינו במכרז אובייקט הגדרה אישית
  • custom_audience_bidding_signals: אובייקט JSON שנוצר על ידי הפלטפורמה. הפורמט של אובייקט ה-JSON הזה הוא:

    var custom_audience_signals = {
      "owner":"ca_owner",
      "buyer":"ca_buyer",
      "name":"ca_name",
      "activation_time":"ca_activation_time_epoch_ms",
      "expiration_time":"ca_expiration_time_epoch_ms",
      "user_bidding_signals":"ca_user_bidding_signals"
    }
    

    איפה:

    • owner, buyer ו-name הם מחרוזת שנלקחה מהנכסים שיש להם את זהה לשם של הקהל בהתאמה אישית שמשתתף בבחירת המודעה
    • activation_time ו-expiration_time הם זמן ההפעלה ו של הקהל בהתאמה אישית, מבוטאת בשניות מאז ה-Unix תקופה של זמן מערכת
    • ca_user_bidding_signals היא מחרוזת JSON שצוינה בקובץ השדה userBiddingSignals בCustomAudience בזמן היצירה
    • trusted_bidding_signals, contextual_signals ו-user_signals הם JSON אובייקטים. הם יועברו כאובייקטים ריקים וימלאו אותם גרסאות עתידיות. הפלטפורמה לא אוכפת את הפורמט שלהן, והוא מנוהל על ידי טכנולוגיית הפרסום.

תוצאה:

  • ad: המודעה שאליה מתייחסת הצעת המחיר. הסקריפט מורשה להחזיר עותק של את המודעה שהוא קיבל עם מטא-נתונים שונים. המאפיין render_url של לא צפויים שינויים.
  • bid: ערך צף שמייצג את ערך הצעת המחיר של המודעה
  • status: ערך של מספר שלם שיכול להיות:
    • 0: לביצוע מוצלח
    • 1: (או כל ערך שאינו אפס) במקרה שאחד מהאותות של הקלט לא חוקי. לחשבון במקרה שבו מוחזר ערך שאינו אפס על ידי יצירת הצעת מחיר, תהליך הבידינג לא תקף לכל מודעות ה-CA

scoreAd()

function scoreAd(
  ad,
  bid,
  ad_selection_config,
  seller_signals,
  trusted_scoring_signals,
  contextual_signal,
  user_signal,
  custom_audience_signal) {
    return {'status': 0, 'score': score };
}

פרמטרים של קלט:

  • ad: יש לעיין במסמכי התיעוד בנושא generateBid
  • bid: ערך הצעת המחיר של המודעה
  • ad_selection_config: אובייקט JSON שמייצג פרמטר AdSelectionConfig של ה-API selectAds. הפורמט היא:

    var ad_selection_config = {
      'seller': 'seller',
      'decision_logic_url': 'url_of_decision_logic',
      'custom_audience_buyers': ['buyer1', 'buyer2'],
      'auction_signals': auction_signals,
      'per_buyer_signals': per_buyer_signals,
      'contextual_ads': [ad1, ad2]
    }
    
  • seller_signals: אובייקטים מסוג JSON שנקראים מהsellerSignals AdSelectionConfig פרמטר API

  • trusted_scoring_signal: קריאה מהשדה adSelectionSignals שבשדה AdSelectionConfig פרמטר API

  • contextual_signals, user_signals: אובייקטים מסוג JSON. כרגע הם מועברים כ- אובייקטים ריקים ויהיו מלאים בגרסאות עתידיות. הפורמט שלהן לא נאכפת על ידי הפלטפורמה ומנוהלת על ידי טכנולוגיית הפרסום.

  • per_buyer_signals: אובייקט JSON שנקרא מהמפה perBuyerSignal AdSelectionConfig פרמטר API שבו נעשה שימוש כמפתח בהתאמה אישית הנוכחית קונה של קהל. ריק אם המפה לא מכילה ערך עבור הנתון הנתון לקונה.

פלט:

  • score: ערך מספר ממשי (float) שמייצג את ערך הציון של המודעה הזו
  • status: ערך של מספר שלם שיכול להיות:
    • 0: לביצוע מוצלח
    • 1: למקרה שהערכים customAudienceSignals לא תקינים
    • 2: למקרה שהשדה AdSelectionConfig לא תקין
    • 3: למקרה שהאותות האחרים לא תקינים
    • כל ערך שאינו אפס גורם לכשל בתהליך, הערך קובע את סוג החריגה שנרשמה

selectOutcome()

function selectOutcome(
  outcomes,
  selection_signals) {
    return {'status': 0, 'result': null};
}

פרמטרים של קלט:

  • outcomes: אובייקט JSON {"id": id_string, "bid": bid_double}
  • selection_signals: אובייקטים של JSON שצוינו בהגדרת המכרז אובייקט

פלט:

  • status: 0 להצלחה, לא אפס לכישלון
  • result: אחת מהתוצאות שהועברו או הערך null

reportResult()

function reportResult(ad_selection_config, render_url, bid, contextual_signals) {
   return {
      'status': status,
      'results': {'signals_for_buyer': signals_for_buyer, 'reporting_url': reporting_url }
   };
}

פרמטרים של קלט:

  • ad_selection_config: אפשר לעיין במסמכי התיעוד של scoreAds
  • render_url: כתובת ה-URL לעיבוד של המודעה הזוכה
  • bid: הצעת המחיר שהוצעה למודעה שזכתה במכרז
  • contextual_signals: אפשר לעיין במסמכי התיעוד של generateBid

פלט:

  • status: 0 להצלחה ולא אפס לכישלון
  • results: אובייקטים מסוג JSON שמכילים:
    • signals_for_buyer: אובייקט JSON שמועבר אל reportWin פונקציה
    • reporting_url: כתובת URL שהפלטפורמה משתמשת בה כדי לשלוח הודעות חשיפה לקונה

reportWin()

function reportWin(
   ad_selection_signals,
   per_buyer_signals,
   signals_for_buyer,
   contextual_signals,
   custom_audience_signals) {
   return {'status': 0, 'results': {'reporting_url': reporting_url } };
}

פרמטרים של קלט:

  • ad_selection_signals, per_buyer_signals: אפשר לעיין במסמכי התיעוד עבור scoreAd
  • signals_for_buyer: אובייקט JSON שהוחזר על ידי reportResult
  • contextual_signals, custom_audience_signals: אפשר לעיין במסמכי התיעוד עבור generateBid

פלט:

  • status: 0 להצלחה ולא אפס לכישלון
  • results: אובייקט JSON שמכיל:
    • reporting_url: כתובת URL שהפלטפורמה משתמשת בה כדי לשלוח הודעות חשיפה למפיץ

registerAdBeacon()

function registerAdBeacon(
  beacons
)

פרמטרים לקליטת נתונים:

  • beacons: אובייקט שמכיל צמדי מפתח-ערך של מפתחות אינטראקציה לדיווח על URI. הפורמט הוא:

    let beacons = {
      'interaction_key': 'reporting_uri',
      'interaction_key': 'reporting_uri',
      ...
    }
    
    • interaction_key: מחרוזת שמייצגת את האירוע. משמש את בשלב מאוחר יותר, כשתדווח על אינטראקציות עם אירועים כדי לחפש את reporting_uri שצריך לקבל הודעה. המפתח הזה צריך להתאים בין מה הקונה או המפיץ רושם, ומה המוכר מדווח.
    • reporting_uri: URI לקבלת דוחות אירועים. זה צריך להיות ספציפי לסוג האירוע המדווח. עליו לקבל בקשת POST כדי לטפל נתונים כלשהם שידווחו יחד עם האירוע.

    לדוגמה:

      let beacons = {
        'click': 'https://reporting.example.com/click_event',
        'view': 'https://reporting.example.com/view_event'
      }
    

מזהי URI מוכנים מראש לבחירת מודעות

מזהי URI מובנים מראש מאפשרים לטכנולוגיות הפרסום להקצות פונקציות JavaScript למודעה לוגיקת ההחלטות של הבחירה בעמודה AdSelectionConfig AdSelectionFromOutcomesConfig כיתות. למזהי URI מובנים אין צורך ברשת קריאות להורדת ה-JavaScript התואם. טכנולוגיות הפרסום יכולות להשתמש במזהי URI מוכנים מראש בלי להגדיר דומיין רשום לאירוח ה-JavaScript.

ה-URI המוגדר מראש נבנה באמצעות הפורמט הבא:

ad-selection-prebuilt:<use-case>/<name>?<required-script-generation-parameters>

פלטפורמת ארגז החול לפרטיות מספקת JavaScript באמצעות המידע URI בסביבת זמן הריצה.

מתבצעת דחייה של IllegalArgumentException אם:

  • אחד מהפרמטרים הנדרשים לא נמצא ב-URI
  • יש פרמטרים לא מזוהים ב-URI

תרחישים לדוגמה ושמות נתמכים של URI מוכן מראש

תרחיש לדוגמה 1: בחירת מודעות

מזהי URI מוכנים מראש בתרחיש לדוגמה של ad-selection נתמכים תהליך של selectAds(AdSelectionConfig).

שם ה-URI המוגדר מראש: highest-bid-wins

ה-URI המובנה הזה מספק JavaScript שבוחר את המודעה עם הצעת המחיר הגבוהה ביותר אחרי הבידינג. היא גם מספקת פונקציית דיווח בסיסית כדי לדווח על render_uri ו-bid של הזוכה.

פרמטרים נדרשים

reportingUrl: כתובת ה-URL הבסיסית לדיווח, שנוספה לפרמטר render_uri וה-bid של המודעה הזוכה:

<reportingUrl>?render_uri=<renderUriOfWinnigAd>&bid=<bidOfWinningAd>

שימוש

אם כתובת ה-URL לדיווח בסיסי היא https://www.ssp.com/reporting, אז הכתובת שהוגדרה מראש ה-URI יהיה:

`ad-selection-prebuilt://ad-selection/highest-bid-wins/?reportingUrl=https://www.ssp.com/reporting`

תרחיש לדוגמה 2: בחירת מודעה מתוצאות החיפוש

מזהי URI מובנים מראש בתרחיש לדוגמה של ad-selection-from-outcomes תומכים תהליך עבודה של selectAds(AdSelectionFromOutcomesConfig).

שם ה-URI המוגדר מראש: waterfall-mediation-truncation

ה-URI המובנה מראש waterfall-mediation-truncation מספק JavaScript הטמעת לוגיקה של קטיעת תהליך בחירת הרשת (Mediation) ב-Waterfall שבו קוד ה-JavaScript מחזיר מודעה של צד ראשון אם הערך של bid גבוה מהערך bid floor או שווה לו, וגם אחרת, הפונקציה מחזירה null.

פרמטרים נדרשים

bidFloor: המפתח של ערך הסף התחתון להצעת המחיר שהועברה ב-getSelectionSignals() שמשווה למודעה של ה-SDK של תהליך בחירת הרשת.

שימוש

אם האותות של בחירת המודעות נראים כך: {"bid_floor": 10}, התוצאות ה-URI המוגדר מראש יהיה:

`ad-selection-prebuilt://ad-selection-from-outcomes/waterfall-mediation-truncation/?bidFloor=bid_floor`

בדיקה

כדי לעזור לך להתחיל להשתמש ב-Protected Audience API, יצרנו דוגמה ב-Kotlin וב-Java, שנמצאות ב-GitHub.

דרישות מוקדמות

Protected Audience API מצריך JavaScript בזמן בחירת המודעה, דיווח על חשיפות. יש שתי שיטות לספק את ה-JavaScript סביבת בדיקה:

  • מריצים שרת עם נקודות הקצה (endpoints) הנדרשות של HTTPS שמחזירות את ה-JavaScript.
  • ביטול אחזור מרחוק על ידי אספקת הקוד הדרוש ממקור מקומי

בכל אחת מהשיטות צריך להגדיר נקודת קצה (endpoint) מסוג HTTPS כדי לטפל בחשיפות דיווח.

נקודות קצה ב-HTTPS

כדי לבדוק את בחירת המודעות ואת הדיווח על החשיפות, צריך להגדיר 7 HTTPS נקודות הקצה שמכשיר הבדיקה או האמולטור שלך יכולים לגשת אליהן:

  1. נקודת הקצה של הקונה שמציגה את ה-JavaScript של לוגיקת הבידינג.
  2. נקודת קצה (endpoint) שמספקת את האותות של הבידינג.
  3. נקודת הקצה של בית העסק שמציגה את ה-JavaScript של לוגיקת ההחלטות.
  4. נקודת קצה (endpoint) שמציגה אותות ניקוד.
  5. נקודת קצה לדיווח על חשיפות של קונה זוכה.
  6. נקודת קצה לדיווח על חשיפות של בית העסק.
  7. נקודת קצה להצגת העדכונים היומיים לקהל בהתאמה אישית.

לנוחיותכם, המאגר של GitHub מספק קוד JavaScript בסיסי לצורך בדיקה. למטרות. הוא כולל גם הגדרות של שירות OpenAPI שניתן לפרוס פלטפורמת הדמיה נתמכת או פלטפורמה מיקרו-שירותים (microservices). פרטים נוספים זמינים בפרויקט README.

ביטול אחזור מרחוק של JavaScript

התכונה הזו מיועדת לשימוש בבדיקת 'קצה-לקצה'. כדי לשנות את ההגדרות של השלט הרחוק אחזור, האפליקציה שלך חייבת לפעול במצב ניפוי באגים כשהאפשרויות למפתחים מופעלות.

כדי להפעיל את מצב ניפוי הבאגים באפליקציה, צריך להוסיף את השורה הבאה לקטע במאפיין האפליקציה בקובץ AndroidManifest.xml:

<application
  android:debuggable="true">

לדוגמה, כיצד להשתמש בביטולים האלו, אפשר לעיין במדיניות 'Protected' אפליקציה לדוגמה של Audience API ב-GitHub.

עליך להוסיף JavaScript מותאם אישית משלך כדי לטפל בתרחישים של בחירת מודעות כמו כמו בידינג, דירוג, החלטות ודיווח. ניתן למצוא קוד JavaScript בסיסי דוגמאות לטיפול בכל הבקשות הנדרשות במאגר GitHub. האפליקציה לדוגמה של Protected Audience API מדגימה איך לקרוא קוד מ- את הקובץ ולהכין אותו לשימוש כשינוי מברירת המחדל.

אפשר לבטל אחזור JavaScript בצד המוכר ובצד הקונה בנפרד, אבל צריך נקודת קצה (endpoint) מסוג HTTPS כדי להציג כל JavaScript שלא הגדרת עבורם שינויים מברירת המחדל. אפשר לעיין בREADME של על ההגדרה של שרת שמטפל בבקשות האלה.

אפשר לבטל אחזור של JavaScript רק לקהלים מותאמים אישית הם בבעלות החבילה שלך.

שינוי JavaScript בצד המוכר

כדי להגדיר שינוי מברירת המחדל של JavaScript בצד המוכר, מבצעים את הפעולות הבאות כפי שמתואר בדוגמת הקוד הבאה:

  1. מאתחלים אובייקט AdSelectionManager.
  2. אפשר לקבל הפניה אל TestAdSelectionManager מ אובייקט AdSelectionManager.
  3. בונים אובייקט AdSelectionConfig.
  4. ליצור AddAdSelectionOverrideRequest עם אובייקט AdSelectionConfig ו-String שמייצג את ה-JavaScript שמתכוונים להשתמש בו בתור שינוי מברירת המחדל.
  5. קריאה לשיטה overrideAdSelectionConfigRemoteInfo() האסינכרונית עם אובייקט AddAdSelectionOverrideRequest ורלוונטי Executor ו-OutcomeReceiver אובייקטים.

Kotlin

val testAdSelectionManager: TestAdSelectionManager =
  context.getSystemService(AdSelectionManager::class.java).getTestAdSelectionManager()

// Initialize AdSelectionConfig =
val adSelectionConfig = new AdSelectionConfig.Builder()
    .setSeller(seller)
    .setDecisionLogicUrl(decisionLogicUrl)
    .setCustomAudienceBuyers(customAudienceBuyers)
    .setAdSelectionSignals(adSelectionSignals)
    .setSellerSignals(sellerSignals)
    .setPerBuyerSignals(perBuyerSignals)
    .build()

// Initialize AddAddSelectionOverrideRequest
val request = AddAdSelectionOverrideRequest.Builder()
    .setAdSelectionConfig(adSelectionConfig)
    .setDecisionLogicJs(decisionLogicJS)
    .build()

// Run the call to override the JavaScript for the given AdSelectionConfig
// Note that this only takes effect in apps marked as debuggable
testAdSelectionManager.overrideAdSelectionConfigRemoteInfo(
    request,
    executor,
    outComeReceiver)

Java

TestAdSelectionManager testAdSelectionManager =
  context.getSystemService(AdSelectionManager.class).getTestAdSelectionManager();

// Initialize AdSelectionConfig =
AdSelectionConfig adSelectionConfig = new AdSelectionConfig.Builder()
    .setSeller(seller)
    .setDecisionLogicUrl(decisionLogicUrl)
    .setCustomAudienceBuyers(customAudienceBuyers)
    .setAdSelectionSignals(adSelectionSignals)
    .setSellerSignals(sellerSignals)
    .setPerBuyerSignals(perBuyerSignals)
    .build();

// Initialize AddAddSelectionOverrideRequest
AddAdSelectionOverrideRequest request = AddAdSelectionOverrideRequest.Builder()
    .setAdSelectionConfig(adSelectionConfig)
    .setDecisionLogicJs(decisionLogicJS)
    .build();

// Run the call to override the JavaScript for the given AdSelectionConfig
// Note that this only takes effect in apps marked as debuggable
testAdSelectionManager.overrideAdSelectionConfigRemoteInfo(
    request,
    executor,
    outComeReceiver);

בקטע הפעלת בחירת מודעות מפורט מידע נוסף על התוכן השדות ב-AdSelectionConfig מייצגים. ההבדל המרכזי הוא אפשר להגדיר את ה-decisionLogicUrl לערך placeholder כפי שיהיה המערכת מתעלמת ממנו.

כדי לשנות את קוד ה-JavaScript שמשמש לבחירת המודעות, המאפיין התג decisionLogicJs חייב לכלול חתימות מתאימות של פונקציות בצד המוכר. כדי לראות דוגמה לקריאת קובץ JavaScript כמחרוזת, אפשר לעיין ב- אפליקציה לדוגמה של Protected Audience API ב-GitHub.

השיטה האסינכרונית overrideAdSelectionConfigRemoteInfo() משתמשת ב אובייקט OutcomeReceiver לציון תוצאת הקריאה ל-API.

הקריאה החוזרת onResult() מציינת שהביטול הוחל בהצלחה. שיחות עתידיות אל selectAds() יתבססו על כל החלטה ודיווח הלוגיקה שהעברתם כשינוי מברירת המחדל.

הקריאה החוזרת של onError() מציינת שני תנאים אפשריים:

  • אם יתבצע ניסיון לשנות מברירת המחדל עם ארגומנטים לא חוקיים, AdServiceException מציין IllegalArgumentException בתור סיבה.
  • אם נעשה ניסיון לשנות מברירת המחדל ואפליקציה שלא פועלת במצב ניפוי באגים עם אפשרויות למפתחים מופעלות, AdServiceException מציין IllegalStateException הוא הגורם לבעיה.

איפוס השינויים מברירת המחדל בצד המוכר

הקטע הזה מניח שעקפתם את קוד ה-JavaScript בצד המוכר יש לכם הפניה אל TestAdSelectionManager AdSelectionConfig היה בשימוש בקטע הקודם.

כדי לאפס את השינויים מברירת המחדל לכל הפריטים ב-AdSelectionConfigs:

  1. הפעלה של שיטת resetAllAdSelectionConfigRemoteOverrides() האסינכרונית עם האובייקט הרלוונטי OutcomeReceiver.

Kotlin

// Resets overrides for all AdSelectionConfigs
testAadSelectionManager.resetAllAdSelectionConfigRemoteOverrides(
  outComeReceiver)

Java

// Resets overrides for all AdSelectionConfigs
testAdSelectionManager.resetAllAdSelectionConfigRemoteOverrides(
    outComeReceiver);

לאחר איפוס השינויים בצד המוכר, קריאות ל-selectAds() ישתמשו בכל הפרמטר decisionLogicUrl מאוחסן ב-AdSelectionConfig כדי לנסות מאחזרת את ה-JavaScript הדרוש.

אם הקריאה ל-resetAllAdSelectionConfigRemoteOverrides() תיכשל, הקריאה החוזרת של OutComeReceiver.onError() מספקת AdServiceException. אם נעשה ניסיון להסיר את השינויים מברירת המחדל ואפליקציה שלא פועלת במצב ניפוי באגים כאשר האפשרויות למפתחים מופעלות, AdServiceException מציין IllegalStateException הוא הגורם לבעיה.

ביטול JavaScript בצד הקונה

  1. פועלים לפי השלבים להצטרפות לקהל בהתאמה אישית.
  2. יצירת AddCustomAudienceOverrideRequest עם הקונה ושם הקהל בהתאמה אישית שרוצים לשנות, בנוסף הלוגיקה של הבידינג והנתונים שבהם רוצים להשתמש כשינוי מברירת המחדל
  3. קריאה לשיטה overrideCustomAudienceRemoteInfo() האסינכרונית עם אובייקט AddCustomAudienceOverrideRequest ורלוונטי Executor ו-OutcomeReceiver אובייקטים

Kotlin

val testCustomAudienceManager: TestCustomAudienceManager =
  context.getSystemService(CustomAudienceManager::class.java).getTestCustomAudienceManager()

// Join custom audience

// Build the AddCustomAudienceOverrideRequest
val request = AddCustomAudienceOverrideRequest.Builder()
    .setBuyer(buyer)
    .setName(name)
    .setBiddingLogicJs(biddingLogicJS)
    .setTrustedBiddingSignals(trustedBiddingSignals)
    .build()

// Run the call to override JavaScript for the given custom audience
testCustomAudienceManager.overrideCustomAudienceRemoteInfo(
    request,
    executor,
    outComeReceiver)

Java

TestCustomAudienceManager testCustomAudienceManager =
  context.getSystemService(CustomAudienceManager.class).getTestCustomAudienceManager();

// Join custom audience

// Build the AddCustomAudienceOverrideRequest
AddCustomAudienceOverrideRequest request =
    AddCustomAudienceOverrideRequest.Builder()
        .setBuyer(buyer)
        .setName(name)
        .setBiddingLogicJs(biddingLogicJS)
        .setTrustedBiddingSignals(trustedBiddingSignals)
        .build();

// Run the call to override JavaScript for the given custom audience
testCustomAudienceManager.overrideCustomAudienceRemoteInfo(
    request,
    executor,
    outComeReceiver);

הערכים של buyer ושל name זהים לאלה ששימשו ליצירה הקהל בהתאמה אישית. למידע נוסף על השדות האלה

אפשר גם לציין שני פרמטרים נוספים:

  • biddingLogicJs: JavaScript שמכיל את הלוגיקה של הקונה שבה נעשה שימוש במהלך בחירת המודעות. כאן מופיעות חתימות הפונקציות הנדרשות. JavaScript.
  • trustedBiddingSignals: האותות לבידינג שבהם צריך להשתמש במהלך בחירת המודעות. למטרות בדיקה, הערך הזה יכול להיות מחרוזת ריקה.

השיטה האסינכרונית overrideCustomAudienceRemoteInfo() משתמשת ב אובייקט OutcomeReceiver כדי לאותת את תוצאת הקריאה ל-API.

הקריאה החוזרת onResult() מציינת שהביטול הוחל בהצלחה. הקריאות הבאות אל selectAds() משתמשות בלוגיקת בידינג ובדיווח כלשהי העברת כשינוי מברירת המחדל.

הקריאה החוזרת (callback) של onError() מציינת שני תנאים אפשריים.

  • אם יתבצע ניסיון לשנות מברירת המחדל עם ארגומנטים לא חוקיים, AdServiceException מציין IllegalArgumentException בתור סיבה.
  • אם נעשה ניסיון לשנות מברירת המחדל ואפליקציה שלא פועלת במצב ניפוי באגים עם אפשרויות למפתחים מופעלות, AdServiceException מציין IllegalStateException הוא הגורם לבעיה.

איפוס שינויים מברירת המחדל בצד הקונה

קטע זה מתבסס על ההנחה ששינית את קוד ה-JavaScript בצד הקונה, יש לך הפניה אל TestCustomAudienceManager שנעשה בו שימוש בקטע הקודם.

כדי לאפס את השינויים מברירת המחדל של כל הקהלים בהתאמה אישית:

  1. קריאה לשיטה resetAllCustomAudienceOverrides() האסינכרונית עם אובייקטים רלוונטיים מסוג Executor ו-OutcomeReceiver.

Kotlin

// Resets overrides for all custom audiences
testCustomAudienceManager.resetCustomAudienceRemoteInfoOverride(
    executor,
    outComeReceiver)

Java

// Resets overrides for all custom audiences
testCustomAudienceManager.resetCustomAudienceRemoteInfoOverride(
    executor,
    outComeReceiver)

לאחר איפוס השינויים בצד הקונה, השיחות הבאות אל selectAds() להשתמש בכל מה שמופיע ב-biddingLogicUrl וב-trustedBiddingData מאוחסנים במסגרת CustomAudience כדי לנסות לאחזר את הנתונים הדרושים. JavaScript.

אם הקריאה ל-resetCustomAudienceRemoteInfoOverride() תיכשל, הקריאה החוזרת של OutComeReceiver.onError() מספקת AdServiceException. אם נעשה ניסיון להסיר את השינויים מברירת המחדל ואפליקציה שלא פועלת במצב ניפוי באגים כשהאפשרות 'אפשרויות למפתחים' מופעלת, ה-AdServiceException מציין IllegalStateException הוא הגורם לבעיה.

הגדרה של שרת דיווח

כשמשתמשים בשינוי מברירת המחדל של אחזור מרחוק, עדיין צריך להגדיר שרת שהמכשיר או האמולטור יכולים להגיע אליהם כדי להגיב לאירועי דיווח. קובץ נקודת קצה שמחזירה 200 מספיקה לבדיקה. המאגר של GitHub כולל הגדרות של שירות OpenAPI שניתן לפרוס להדמיה נתמכת או ובפלטפורמת מיקרו-שירותים. פרטים נוספים זמינים בפרויקט README.

כשמחפשים את ההגדרות של OpenAPI, צריך לחפש את הקובץ report-server.json. הקובץ הזה מכיל נקודת קצה פשוטה שמחזירה את 200, שמייצגת HTTP קוד תגובה. נקודת הקצה (endpoint) הזו נמצאת בשימוש במהלך selectAds() ומציינת ל Protected Audience API שדיווח על חשיפות הושלם בהצלחה.

פונקציונליות לבדיקה

  • תרגיל הצטרפות או עזיבה והגדרת קהל בהתאמה אישית לפי פעולות משתמש.
  • התחלת בחירת המודעות במכשיר באמצעות JavaScript שמתארחים מרחוק.
  • לבדוק איך שיוך של אפליקציה להגדרות קהלים בהתאמה אישית עשוי להשפיע על המודעה או תוצאות בחירה.
  • מקבלים דיווח על חשיפות אחרי בחירת המודעות.

מגבלות

בטבלה הבאה מפורטות המגבלות על עיבוד Protected Audience API. המגבלות שמוצגות עשויות להשתנות בהתאם למשוב. עבור יכולות בתהליך, יש לקרוא את נתוני הגרסה.

רכיב תיאור המגבלה ערך מגבלה
קהל בהתאמה אישית (CA) מספר מודעות מקסימלי לכל CA 100
המספר המקסימלי של רשויות אישורים לכל בקשה 1000
מספר האפליקציות המקסימלי שיכול ליצור רשות אישורים 1000
העיכוב המקסימלי בזמן ההפעלה של רשות אישורים ממועד היצירה שלה 60 ימים
זמן התפוגה המקסימלי של רשות אישורים (CA) מזמן ההפעלה שלה 60 ימים
המספר המקסימלי של רשויות אישורים במכשיר 4000
הגודל המקסימלי של שם ה-CA 200 בייטים
הגודל המקסימלי של URI לאחזור יומי 400 בייטים
הגודל המקסימלי של ה-URI של לוגיקת הבידינג 400 בייטים
הגודל המקסימלי של נתוני בידינג מהימנים 10 KB
הגודל המקסימלי של האותות לבידינג המשתמשים 10 KB
שיעור שיחות מקסימלי ב-leaveCustomAudience לכל קונה 1 לשנייה
שיעור שיחות מקסימלי עבור joinCustomAudience לכל קונה 1 לשנייה
אחזור רקע של קליפורניה פג הזמן הקצוב של החיבור ‫5 שניות
זמן קצוב לתפוגה של קריאת HTTP ‫30 שניות
גודל הורדה כולל מקסימלי 10 KB
משך זמן מקסימלי של איטרציה של אחזור 5 דקות
המספר המקסימלי של רשויות אישורים שעודכנו לכל משימה 1000
בחירת מודעות מספר קונים מקסימלי טרם נקבע
המספר המקסימלי של רשויות אישורים לכל קונה טרם נקבע
המספר המקסימלי של מודעות במכרז טרם נקבע
זמן קצוב ראשוני לתפוגת החיבור ‫5 שניות
הזמן הקצוב לקריאת החיבור פג ‫5 שניות
זמן ביצוע מקסימלי של AdSelection ‫10 שניות
זמן ביצוע מקסימלי של בידינג לכל CA ב-AdSelection 5 שניות
זמן ביצוע מקסימלי של ניקוד ב-AdSelection 5 שניות
זמן ביצוע מקסימלי לכל קונה ב-AdSelection טרם נקבע
הגודל המקסימלי של אותות בחירת המודעה/אתר המכירה/לכל קונה טרם נקבע
הגודל המקסימלי של סקריפטים של אתר מכירה/קונה טרם נקבע
קצב שיחות מקסימלי ב-selectAds QPS אחד
דיווח על חשיפות זמן מינימלי לפני הסרת המודעות שנבחרו מהתמיד 24 שעות
המספר המקסימלי של מודעות האחסון שייבחרו טרם נקבע
הגודל המקסימלי של כתובת URL לפלט הדיווח טרם נקבע
משך זמן מקסימלי לדיווח על חשיפות טרם נקבע
המספר המרבי של ניסיונות חוזרים לשיחות התראה טרם נקבע
תם פרק הזמן שהוקצב להתחברות ‫5 שניות
זמן הביצוע הכולל המקסימלי של reportImpression 2 שניות
קצב שיחות מקסימלי ב-reportImpressions QPS אחד
דיווח על אירועים המספר המקסימלי של משׂואות רשת (beacon) לכל קונה בכל מכרז 10

המספר המקסימלי של משׂואות רשת (beacon) לכל אתר מכירה בכל מכרז

10

הגודל המקסימלי של מפתח האירוע

40 בייטים

הגודל המקסימלי של נתוני האירוע

64KB

מודעות גודל מקסימלי של רשימת מודעות 10KB משותפים לכולם AdData ברשות אישורים אחת לקבלת
URLs האורך המקסימלי של כל מחרוזת כתובת URL שנלקחה כקלט טרם נקבע
JavaScript זמן ביצוע מקסימלי שנייה אחת לבידינג ולציון בדוחות חשיפות
נפח זיכרון מקסימלי ‎10 MB

דיווח על באגים ובעיות

המשוב שלכם הוא חלק חיוני בארגז החול לפרטיות ב-Android. נשמח לשמוע ממך על כל בעיות שמצאתם או רעיונות לשיפור ארגז החול לפרטיות ב-Android.