Monetization Provider API

版本:1.0.0

簡介

您可以使用營利服務供應商用戶端 API,將自家的營利解決方案與 Ad Manager 中的「隱私權與訊息」整合。

如要將自己的營利解決方案與 Offerwall 整合,請按照下列步驟操作:

  • 在 Ad Manager 的「隱私權與訊息」分頁中,為 Offerwall 啟用「自訂選項」選項。

  • 在發布 Offerwall 的網站上新增自訂 JavaScript。如要瞭解實作方式的詳細資訊,請參閱下文。

  • 這段 JavaScript 應依下方定義,將自訂營利服務供應器例項化,並在視窗上使用 註冊金鑰 'publisherCustom' 向 Privacy & Messaging 註冊供應器。

詞彙

字詞 定義
營利服務供應商 提供自訂營利解決方案的原生 JavaScript 物件。舉例來說,您可以提供訂閱服務、微支付服務等等。Offerwall 會叫用供應商的方法,透過自訂解決方案從內容中營利。
授權 當使用者完成某些營利動作時,營利解決方案會授予使用者這類獎勵。在這個 API 的範圍內,授權可讓使用者存取網站內容,而不會看到 Offerwall。您可以決定為選擇自訂營利選項的使用者提供免費網頁載入次數或時間長度。
營利入口網站 營利流程的進入點。入口網站會定義營利解決方案提供的個別流程。舉例來說,一個入口網站可以用於「營利」,讓使用者訂閱您的服務。另一個入口網站可能用於「登入」,讓使用者登入現有訂閱項目。
註冊金鑰 營利服務供應商的 ID,用於在網頁載入時,將供應商實作項目註冊至 Google 隱私權與訊息。

API 實作範例

以下是實作範例,其中定義了營利服務供應器、將其例項化,並向 Google 隱私權與訊息服務註冊。

<script>
  // This class defines a monetization provider by implementing four core functions that every provider
  // must support: initialize, getUserEntitlementState, monetize, and destroy.
  class CustomMonetizationProvider {
    userEntitlementState;

    async initialize(initializeParams) {
      // Replace this function's code with your implementation of the initialize function.
      this.userEntitlementState = googlefc.monetization.UserEntitlementStateEnum.ENTITLED_NO;
      return {initializeSuccess: true, apiVersionInUse: "1.0.0", signInMonetizationPortalSupported: false};
    }

    async getUserEntitlementState() {
      // Replace this function's code with your implementation of the getUserEntitlementState function.
      return this.userEntitlementState;
    }

    async monetize(monetizeParams) {
      // Replace this function's code with your implementation of the monetize function.
      if (monetizeParams.monetizationPortal == googlefc.monetization.MonetizationPortalEnum.PORTAL_PRIMARY_ACCESS) {
        return await this.showSubscriptionPrompt();
      } else {
        console.log('Unsupported monetization portal.');
      }
    }

    async destroy(destructionParams) {
      // Replace this function's code with your implementation of the destroy function.
      console.log('Custom provider is no longer initialized.');
    }

    // ==== The helper functions in this section are only used for this demo, and should be omitted from your actual implementation. ===
    async showSubscriptionPrompt() {
      return new Promise(resolve => {
        const sharedStyles = 'border: 2px solid #6b6e7666; border-radius: 8px; padding: 10px; background: white;';
        const modalStyles =  'width: 500px; z-index: 100; top: 50%; left: 50%; position: absolute; transform: translate(-50%, -50%);';
        const overlayStyles = 'height: 100%; width: 100%; background: black; opacity: 0.6; z-index: 99; position: absolute; top: 0;';

        const modal = this.createElement("div", modalStyles + sharedStyles);
        const overlay = this.createElement("div", overlayStyles);
        const header = this.createElement("h1", 'text-align: center; color: black;', "Subscribe for access.");
        const subscribeButton = this.createElement("button", sharedStyles + 'color: #5499C7; margin-left: 40%;', "Subscribe");
        const backButton = this.createElement("button", sharedStyles + 'color: #5499C7;', "Back");

        this.exitSubscriptionPromptOnButtonClick(subscribeButton, resolve, googlefc.monetization.UserEntitlementStateEnum.ENTITLED_YES, modal, overlay);
        this.exitSubscriptionPromptOnButtonClick(backButton, resolve, googlefc.monetization.UserEntitlementStateEnum.ENTITLED_NO,modal, overlay);

        modal.append(backButton, header, subscribeButton);
        document.body.append(overlay, modal);
      });
    }

    createElement(tag, styles = '', textContent ='') {
      const element = document.createElement(tag);
      element.style.cssText = styles;
      element.textContent = textContent;
      return element;
    }

    exitSubscriptionPromptOnButtonClick(button, resolve, userEntitlementStateEnum, modal, overlay) {
      button.addEventListener("click", () => {
        document.body.removeChild(modal);
        document.body.removeChild(overlay);
        this.userEntitlementState = userEntitlementStateEnum;
        resolve({userEntitlementState: userEntitlementStateEnum});
      });
    }
    // =============================================================================================================================
  };

  // Important: code to register a custom monetization provider with Google Privacy & messaging.
  window.googlefc = window.googlefc || {};
  window.googlefc.monetization = window.googlefc.monetization || {};
  window.googlefc.monetization.providerRegistry =
    window.googlefc.monetization.providerRegistry || new Map();

  window.googlefc.monetization.providerRegistry.set(
    'publisherCustom', new CustomMonetizationProvider());
</script>

上方的程式碼片段是骨架實作,包含整合營利服務供應商與「隱私權與訊息」所需的所有內容。請注意,針對每個供應器函式,我們都已新增範例程式碼,請自行負責將其替換為自己的實作項目。

方法摘要

營利供應器是一種物件,可透過公開核心函式組合,在網頁上提供營利功能。這些函式說明如下。

方法 摘要
initialize 初始化營利供應器,以及執行營利動作所需的任何資源。
getUserEntitlementState 在叫用時取得使用者的授權狀態。
monetize 在網頁上顯示自訂營利解決方案。營利解決方案可以採用任何形式,例如獎勵廣告、訂閱服務對話方塊等。
destroy 銷毀提供者,以及在初始化時執行的任何資源或工作。在銷毀時,Offerwall 就不會再叫用任何提供者方法。

方法定義

以下進一步說明各項營利服務供應商方法的定義。

initialize

initialize(initializeParams:InitializeParams): Promise<InitializeResponse>

初始化營利服務供應器。初始化後,提供者應可回應任何其他提供者函式。此函式保證會在任何其他提供者函式之前叫用,且在特定頁面載入時最多只會叫用一次。

範例:

  async initialize(initializeParams: InitializeParams): Promise<InitializeResponse> {
    const isInitializationSuccessful = await this.initializeMyProvider(initializeParams);
    const initializeResponse = {initializeSuccess: isInitializationSuccessful,
                                                   apiVersionInUse: "1.0.0",
                                                   signInMonetizationPortalSupported: true};
    resolve(initializeResponse);
  }

getUserEntitlementState

getUserEntitlementState(): Promise<UserEntitlementStateEnum>

在叫用時取得使用者的授權狀態。如果使用者有權存取網站,系統會隱藏 Offerwall,因為使用者應可免費存取網站。

範例:

  async getUserEntitlementState(): Promise<googlefc.monetization.UserEntitlementStateEnum> {
      resolve(this.isUserLoggedIn() ? this.isUserEntitledOnThisPage()
        : googlefc.monetization.UserEntitlementStateEnum.ENTITLED_NO);
  }

營利

monetize(monetizeParams:MonetizeParams): Promise<MonetizeResponse>

算繪營利解決方案,並處理使用者的營利動作。營利方式可以是任何形式,例如獎勵廣告、訂閱服務等。Offerwall 叫用這個方法後,Offerwall 會隱藏,直到 promise 解除為止。因此,供應商有責任在承諾解決前,將網頁內容設為待審核狀態。承諾解決後,供應器也必須確保不再顯示在網頁上。

強烈建議您在營利解決方案中使用 InitializeParams 中提供的建議語言程式碼和樣式。這可確保 Offerwall 和供應商之間的視覺體驗順暢無礙。

Offerwall 會設定營利入口網站參數,指出要存取哪個入口網站。可用的兩種入口網站類型包括 PORTAL_PRIMARY_ACCESS (非選用) 和 PORTAL_SIGN_IN (選用)。您可以透過對 initialize 函式的回應,指出是否支援選用的入口網站 PORTAL_SIGN_IN

解析營利函式 promise 後,您必須:

  • 隱藏已算繪的營利解決方案。

  • 傳回使用者是否有權存取網頁內容。這會決定 Offerwall 是否繼續顯示或隱藏。

  • 傳回使用者互動情形的任何其他資料 (如適用),例如付款金額、授權類型和值,以及營利活動的週期。

範例:

  async monetize(monetizeParams: MonetizeParams): Promise<MonetizeResponse> {
    const result;
    if (monetizeParams.monetizationPortal == googlefc.monetization.MonetizationPortalEnum.PORTAL_PRIMARY_ACCESS) {
      result = await this.showMyBuyFlow();
    } else if (monetizeParams.monetizationPortal == googlefc.monetization.MonetizationPortalEnum.PORTAL_SIGN_IN) {
      result = await this.showMySignInFlow();
    }

    if (!result.monetized) {
      resolve({userEntitlementState: googlefc.monetization.UserEntitlementStateEnum.ENTITLED_NO});
    }

    const monetizeResponse = {
      userEntitlementState: googlefc.monetization.UserEntitlementStateEnum.ENTITLED_YES,
      newlyGrantedUserEntitlementType: googlefc.monetization.EntitlementTypeEnum.TYPE_PAGEVIEW_COUNT,
      newlyGrantedUserEntitlementValue: 4,
      newlyPaidAmountByUser: {currencyCode: "USD", units: 5, nanos: 0},
      // This monetization event does not auto-recur, so leaving property
      // recurrenceOfNewMonetizationEvent undefined.
    }
    resolve(monetizeResponse);
  }

destroy

destroy(destroyParams:DestroyParams): void

刪除提供者。此函式保證會在提供者的生命週期中最後一個被叫用,且在特定網頁載入時最多只會被叫用一次。

範例:

  destroy(destroyParams: DestroyParams): void {
    this.recordDestroyReason(destroyParams.destroyReason);
    this.destroyAllOfMyResourcesOnPage();
  }

類型定義

下文將進一步說明 API 中各個資料類型的定義。

物件定義

本節列出 API 中的所有物件定義。

InitializeParams

initialize 函式的參數類型。

interface InitializeParams {
  // The loaded monetization provider API version. i.e. "1.0.0"
  currentApiVersion: string;
  // The language code suggested for the provider to use, as defined by BCP 47.
  suggestedLanguageCode?: string;
  // The styles suggested for the provider to use.
  suggestedStyles?: Styles;
  // The publisher's logo url.
  publisherLogoUrl?: string;
}

Styles

定義樣式的類型。

interface Styles {
  // The primary color of the Offerwall.
  primaryColor?: string;
  // The background color of the Offerwall.
  backgroundColor?: string;
}

InitializeResponse

initialize 函式的回應類型。

interface InitializeResponse {
  // Whether or not initialization was successful. If initialization is
  // unsuccessful, the Offerwall does not proceed to call other provider methods
  // except for destroy.
  initializeSuccess: boolean;
  // The monetization provider API version that the provider is using. If the
  // indicated major version is not equal to the major version of the API
  // currently on the page, provider execution is halted.
  apiVersionInUse: string;
  // Whether or not the optional sign-in monetization portal is supported. If
  // you indicate that it is supported, the Offerwall renders a sign-in link
  // that will invoke your sign-in portal upon user click.
  signInMonetizationPortalSupported: boolean;
  // Whether or not the provider is disabled. If disabled, the Offerwall can
  // only render with other eligible choices; if no other choices are eligible,
  // the Offerwall won't ever render on the page.
  isProviderDisabled?: boolean;
}

MonetizeParams

monetize 函式的參數類型。

interface MonetizeParams {
  // The monetization portal that the Offerwall wants to invoke. You can
  // indicate whether you support any optional portals in your
  // InitializeResponse; the only portal that isn't optional is
  // MonetizationPortalEnum.PORTAL_PRIMARY_ACCESS. The Offerwall provides the
  // portal enum for the flow requested by the user.
  monetizationPortal: googlefc.monetization.MonetizationPortalEnum;
}

MonetizeResponse

monetize 函式的回應類型。

interface MonetizeResponse {
  // The user's current entitlement state.
  userEntitlementState: googlefc.monetization.UserEntitlementStateEnum;
  // The user's granted entitlement type, only populated if an entitlement was
  // granted within the scope of the current MonetizationProvider.monetize
  // invocation.
  newlyGrantedUserEntitlementType?: googlefc.monetization.EntitlementTypeEnum;
  // The user's granted entitlement value, only populated if an entitlement was
  // granted within the scope of the current MonetizationProvider.monetize
  // invocation.
  newlyGrantedUserEntitlementValue?: number;
  // The amount paid by the user, only populated if a payment occurred within
  // the scope of the current MonetizationProvider.monetize invocation.
  newlyPaidAmountByUser?: Money;
  // The recurrence of the monetization event, populated only if the
  // monetization event occurred within the scope of the current
  // MonetizationProvider.monetize invocation & the monetization event is
  // expected to auto-recur without further action from the user (e.g.
  // registering for a monthly subscription)
  recurrenceOfNewMonetizationEvent?: googlefc.monetization.MonetizationRecurrenceEnum;
}

Money

用於定義特定貨幣金額的類型。請參閱原始 money.proto 定義。

interface Money {
  // The three-letter currency code defined in ISO 4217.
  currencyCode: string;
  // The whole units of the amount.
  // For example if `currencyCode` is `"USD"`, then 1 unit is one US dollar.
  units?: number;
  // Number of nano (10^-9) units of the amount.
  // The value must be between -999,999,999 and +999,999,999 inclusive.
  // If `units` is positive, `nanos` must be positive or zero.
  // If `units` is zero, `nanos` can be positive, zero, or negative.
  // If `units` is negative, `nanos` must be negative or zero.
  // For example $-1.75 is represented as `units`=-1 and `nanos`=-750,000,000.
  nanos?: number;
}

DestroyParams

destroy 函式的參數類型。

interface DestroyParams {
  // The reason for destroying the provider.
  destroyReason: googlefc.monetization.DestroyReasonEnum;
}

列舉定義

本節列出 API 中的所有列舉定義。

googlefc.monetization.UserEntitlementStateEnum

列舉使用者可在營利服務供應商中擁有的授權狀態。

googlefc.monetization.UserEntitlementStateEnum {
  ENTITLED_UNKNOWN = 0,
  // The user is currently entitled to access page content.
  ENTITLED_YES = 1,
  // The user is not currently entitled to access page content.
  ENTITLED_NO = 2,
}

googlefc.monetization.MonetizationPortalEnum

列舉供應商可能支援的不同營利入口網站或營利入口點。如要進一步瞭解營利入口,請參閱詞彙解釋

googlefc.monetization.MonetizationPortalEnum {
  PORTAL_UNKNOWN = 0,
  // The primary access portal represents a provider's main entry point into a
  // monetization flow, and must always be supported.
  PORTAL_PRIMARY_ACCESS = 1,
  // The sign in portal represents a provider's monetization entry point that
  // usually begins with the user performing some sign-in or registration
  // action. Provider support for this monetization portal type is optional.
  PORTAL_SIGN_IN = 2,
}

googlefc.monetization.EntitlementTypeEnum

列舉營利服務供應商可授予使用者的不同授權類型。

googlefc.monetization.EntitlementTypeEnum {
  TYPE_UNKNOWN = 0,
  // This type is used if the user is awarded a positive integer value of
  // Offerwall-free pageviews.
  TYPE_PAGEVIEW_COUNT = 1,
  // This type is used if the user is awarded a positive integer value of
  // seconds (duration) in which they can access Offerwall-free page content any
  // number of times.
  TYPE_DURATION_SECONDS = 2,
}

googlefc.monetization.DestroyReasonEnum

列舉營利供應商可能遭到刪除的原因。

googlefc.monetization.DestroyReasonEnum {
  REASON_UNKNOWN = 0,
  // The Offerwall no longer needs to invoke the monetization provider on the
  // pageview.
  REASON_CALLER_FINISHED = 1,
  // The Offerwall encountered an erroneous state with the monetization provider
  // in the midst of the provider's lifecycle.
  REASON_ERROR_STATE = 2,
  // The API version that the monetization provider is currently using is no
  // longer supported.
  REASON_UNSUPPORTED_API_VERSION = 3,
}

googlefc.monetization.MonetizationRecurrenceEnum

列舉可在某些使用者動作後啟動的不同營利週期。

googlefc.monetization.MonetizationRecurrenceEnum {
  MONETIZATION_RECURRENCE_UNKNOWN = 0,
  MONETIZATION_RECURRENCE_WEEKLY = 1,
  MONETIZATION_RECURRENCE_MONTHLY = 2,
  MONETIZATION_RECURRENCE_ANNUALLY = 3,
}

供應者註冊

googlefc.monetization.providerRegistry?: Map<string, Object>

用於註冊營利服務供應商的視窗層級 JavaScript 物件。註冊程序包括將以靜態註冊金鑰為索引的例項化提供者物件,傳遞至位於視窗命名空間下的註冊中心:window.googlefc.monetization

// Register a custom monetization provider with Google Privacy & messaging.
window.googlefc = window.googlefc || {};
window.googlefc.monetization = window.googlefc.monetization || {};
window.googlefc.monetization.providerRegistry =
                            window.googlefc.monetization.providerRegistry || new Map();

window.googlefc.monetization.providerRegistry.set(
                            'publisherCustom', new CustomMonetizationProvider());

版本記錄

版本 發布日期 摘要
1.0.0 2023 年 7 月 24 日 推出營利服務供應器 API 的初始版本。