开始使用

根据 Google 欧盟地区用户意见征求政策,您必须向位于欧洲经济区 (EEA) 以及英国境内的用户披露相关信息,在法律有相应要求的情况下,必须征得他们的同意才能使用 Cookie 或其他本地存储方式,以及使用个人数据(例如 AdID)来投放广告。此政策反映了欧盟《电子隐私指令》和《一般数据保护条例》(GDPR) 的要求。

为了帮助发布商履行此政策规定的职责,Google 提供了 User Messaging Platform (UMP) SDK。UMP SDK 已更新,可支持最新的 IAB 标准。现在,所有这些配置都可以在 AdMob 隐私权和消息中方便地处理。

前提条件

创建消息类型

在您的 AdMob 账号的隐私权和消息标签页下,使用 可用的用户消息类型 创建用户消息。UMP SDK 会尝试显示通过您项目中设置的 AdMob 应用 ID 创建的用户消息。如果没有为您的应用配置消息,SDK 将返回错误。

如需了解详情,请参阅 隐私权和消息简介

导入 SDK

CocoaPods(首选)

要将 SDK 导入 iOS 项目,最简单的方法就是使用 CocoaPods。打开项目的 Podfile 并将下面这行代码添加到应用的目标中:

pod 'GoogleUserMessagingPlatform'

然后运行以下命令:

pod install --repo-update

如果您刚开始接触 CocoaPods,请参阅使用 CocoaPods,详细了解如何创建和使用 Podfile。

Swift Package Manager

UMP SDK 还支持 Swift Package Manager。请按照以下步骤导入 Swift 软件包。

  1. 在 Xcode 中,前往 File > Add Packages...,安装 UMP SDK Swift 软件包。

  2. 在显示的提示中,搜索 UMP SDK Swift Package GitHub 代码库:

    https://github.com/googleads/swift-package-manager-google-user-messaging-platform.git
    
  3. 选择您要使用的 UMP SDK Swift 软件包版本。对于新项目,我们建议使用 Up to Next Major Version

然后,Xcode 会解析您的软件包依赖项,并在后台下载它们。如需详细了解如何添加软件包依赖项,请参阅 Apple 的文章

手动下载

另一种方法是手动导入 SDK。

下载 SDK

然后,将框架拖动到您的 Xcode 项目中,确保选中 Copy items if needed

然后,您可以将该框架包含在需要使用的任何文件中:

Swift

import UserMessagingPlatform

Objective-C

#include <UserMessagingPlatform/UserMessagingPlatform.h>

您应在每次启动应用时使用 requestConsentInfoUpdateWithParameters:completionHandler:请求更新用户的用户意见征求信息。这决定了您的用户是否需要提供同意声明(如果尚未提供)或同意情况已过期。

以下示例展示了如何在 viewDidLoad() 方法中检查 UIViewController 的状态。

Swift

override func viewDidLoad() {
  super.viewDidLoad()

  // Request an update for the consent information.
  UMPConsentInformation.sharedInstance.requestConsentInfoUpdate(with: nil) {
    [weak self] requestConsentError in
    guard let self else { return }

    if let consentError = requestConsentError {
      // Consent gathering failed.
      return print("Error: \(consentError.localizedDescription)")
    }

    // TODO: Load and present the consent form.
  }
}

Objective-C

- (void)viewDidLoad {
  [super viewDidLoad];

  // Request an update for the consent information.
  [UMPConsentInformation.sharedInstance
      requestConsentInfoUpdateWithParameters:nil
          completionHandler:^(NSError *_Nullable requestConsentError) {
            if (requestConsentError) {
              // Consent gathering failed.
              NSLog(@"Error: %@", requestConsentError.localizedDescription);
              return;
            }

            // TODO: Load and present the consent form.
          }];
}

根据需要加载并显示用户意见征求表单

收到最新的同意情况后,请对UMPConsentForm 类调用loadAndPresentIfRequiredFromViewController:completionHandler: 以加载用户意见征求表单。如果需要用户意见状态,SDK 会加载一个表单,并 通过提供的 view controller立即显示该表单。在用户关闭表单后,系统会调用 completion handler 。如果不需要征得用户同意,系统会立即 completion handler 。

Swift

override func viewDidLoad() {
  super.viewDidLoad()

  // Request an update for the consent information.
  UMPConsentInformation.sharedInstance.requestConsentInfoUpdate(with: nil) {
    [weak self] requestConsentError in
    guard let self else { return }

    if let consentError = requestConsentError {
      // Consent gathering failed.
      return print("Error: \(consentError.localizedDescription)")
    }

    UMPConsentForm.loadAndPresentIfRequired(from: self) {
      [weak self] loadAndPresentError in
      guard let self else { return }

      if let consentError = loadAndPresentError {
        // Consent gathering failed.
        return print("Error: \(consentError.localizedDescription)")
      }

      // Consent has been gathered.
    }
  }
}

Objective-C

- (void)viewDidLoad {
  [super viewDidLoad];

  __weak __typeof__(self) weakSelf = self;
  // Request an update for the consent information.
  [UMPConsentInformation.sharedInstance
      requestConsentInfoUpdateWithParameters:nil
          completionHandler:^(NSError *_Nullable requestConsentError) {
            if (requestConsentError) {
              // Consent gathering failed.
              NSLog(@"Error: %@", requestConsentError.localizedDescription);
              return;
            }

            __strong __typeof__(self) strongSelf = weakSelf;
            if (!strongSelf) {
              return;
            }

            [UMPConsentForm loadAndPresentIfRequiredFromViewController:strongSelf
                completionHandler:^(NSError *loadAndPresentError) {
                  if (loadAndPresentError) {
                    // Consent gathering failed.
                    NSLog(@"Error: %@", loadAndPresentError.localizedDescription);
                    return;
                  }

                  // Consent has been gathered.
                }];
          }];
}

如果您需要在用户做出选择或关闭表单后执行任何操作,请将相应逻辑放在表单的 completion handler中。

提出广告请求

在您的应用中请求广告之前,请检查您是否已使用 UMPConsentInformation.sharedInstance.canRequestAds征得用户同意。在征求用户意见时,有两个位置可供检查:

  1. 在当前会话中收集用户意见后。
  2. 调用 requestConsentInfoUpdateWithParameters:completionHandler:后。可能已在上一次会话中征得用户同意。为缩短延迟时间,我们建议不要等待回调完成,以便在应用启动后尽快开始加载广告。

如果在征求用户意见的过程中出现错误,您仍应尝试请求广告。UMP SDK 会使用上一会话中的用户同意情况。

Swift

class ViewController: UIViewController {

  // Use a boolean to initialize the Google Mobile Ads SDK and load ads once.
  private var isMobileAdsStartCalled = false

  override func viewDidLoad() {
    super.viewDidLoad()

    // Request an update for the consent information.
    UMPConsentInformation.sharedInstance.requestConsentInfoUpdate(with: nil) {
      [weak self] requestConsentError in
      guard let self else { return }

      if let consentError = requestConsentError {
        // Consent gathering failed.
        return print("Error: \(consentError.localizedDescription)")
      }

      UMPConsentForm.loadAndPresentIfRequired(from: self) {
        [weak self] loadAndPresentError in
        guard let self else { return }

        if let consentError = loadAndPresentError {
          // Consent gathering failed.
          return print("Error: \(consentError.localizedDescription)")
        }

        // Consent has been gathered.
        if UMPConsentInformation.sharedInstance.canRequestAds {
          self.startGoogleMobileAdsSDK()
        }
      }
    }
    
    // Check if you can initialize the Google Mobile Ads SDK in parallel
    // while checking for new consent information. Consent obtained in
    // the previous session can be used to request ads.
    if UMPConsentInformation.sharedInstance.canRequestAds {
      startGoogleMobileAdsSDK()
    }
  }
  
  private func startGoogleMobileAdsSDK() {
    DispatchQueue.main.async {
      guard !self.isMobileAdsStartCalled else { return }

      self.isMobileAdsStartCalled = true

      // Initialize the Google Mobile Ads SDK.
      GADMobileAds.sharedInstance().start()

      // TODO: Request an ad.
      // GADInterstitialAd.load(...)
    }
  }
}

Objective-C

@implementation ViewController

- (void)viewDidLoad {
  [super viewDidLoad];

  __weak __typeof__(self) weakSelf = self;
  // Request an update for the consent information.
  [UMPConsentInformation.sharedInstance
      requestConsentInfoUpdateWithParameters:nil
          completionHandler:^(NSError *_Nullable requestConsentError) {
            if (requestConsentError) {
              // Consent gathering failed.
              NSLog(@"Error: %@", requestConsentError.localizedDescription);
              return;
            }
            __strong __typeof__(self) strongSelf = weakSelf;
            if (!strongSelf) {
              return;
            }

            [UMPConsentForm loadAndPresentIfRequiredFromViewController:strongSelf
                completionHandler:^(NSError *loadAndPresentError) {
                  if (loadAndPresentError) {
                    // Consent gathering failed.
                    NSLog(@"Error: %@", loadAndPresentError.localizedDescription);
                    return;
                  }

                  // Consent has been gathered.
                  __strong __typeof__(self) strongSelf = weakSelf;
                  if (!strongSelf) {
                    return;
                  }

                  if (UMPConsentInformation.sharedInstance.canRequestAds) {
                    [strongSelf startGoogleMobileAdsSDK];
                  }
                }];
          }];

  // Check if you can initialize the Google Mobile Ads SDK in parallel
  // while checking for new consent information. Consent obtained in
  // the previous session can be used to request ads.
  if (UMPConsentInformation.sharedInstance.canRequestAds) {
    [self startGoogleMobileAdsSDK];
  }
}

- (void)startGoogleMobileAdsSDK {
  static dispatch_once_t onceToken;
  dispatch_once(&onceToken, ^{
    // Initialize the Google Mobile Ads SDK.
    [GADMobileAds.sharedInstance startWithCompletionHandler:nil];

    // TODO: Request an ad.
    // [GADInterstitialAd loadWithAdUnitID...];
  });
}

隐私设置选项

有些用户意见征求表单会要求用户随时修改同意情况。请根据需要按照以下步骤实现隐私权选项按钮。

要实现这一目标,需要完成以下步骤:

  1. 实现可触发隐私权选项表单的界面元素,例如应用的设置页面中的按钮。
  2. loadAndPresentIfRequiredFromViewController:completionHandler: 完成后,请检查privacyOptionsRequirementStatus 以确定是否显示可呈现隐私权选项表单的界面元素。
  3. 当用户与您的界面元素交互时,调用presentPrivacyOptionsFormFromViewController:completionHandler: 以显示该表单,以便用户能够随时更新其隐私选项。

以下示例展示了如何从 UIBarButtonItem 显示隐私权选项表单。

Swift

@IBOutlet weak var privacySettingsButton: UIBarButtonItem!

var isPrivacyOptionsRequired: Bool {
  return UMPConsentInformation.sharedInstance.privacyOptionsRequirementStatus == .required
}

override func viewDidLoad() {
  // ...

  // Request an update for the consent information.
  UMPConsentInformation.sharedInstance.requestConsentInfoUpdate(with: parameters) {
    // ...

    UMPConsentForm.loadAndPresentIfRequired(from: self) {
      //...

      // Consent has been gathered.

      // Show the button if privacy options are required.
      self.privacySettingsButton.isEnabled = isPrivacyOptionsRequired
    }
  }
  // ...
}

// Present the privacy options form when a user interacts with the
// privacy settings button.
@IBAction func privacySettingsTapped(_ sender: UIBarButtonItem) {
  UMPConsentForm.presentPrivacyOptionsForm(from: self) {
    [weak self] formError in
    guard let self, let formError else { return }

    // Handle the error.
  }
}

Objective-C

@interface ViewController ()
@property(weak, nonatomic) IBOutlet UIBarButtonItem *privacySettingsButton;
@end

- (BOOL)isPrivacyOptionsRequired {
  return UMPConsentInformation.sharedInstance.privacyOptionsRequirementStatus ==
         UMPPrivacyOptionsRequirementStatusRequired;
}

- (void)viewDidLoad {
  // ...

  __weak __typeof__(self) weakSelf = self;
  // Request an update for the consent information.
  [UMPConsentInformation.sharedInstance
      requestConsentInfoUpdateWithParameters:parameters
          completionHandler:^(NSError *_Nullable requestConsentError) {
            // ...

            [UMPConsentForm loadAndPresentIfRequiredFromViewController:strongSelf
                completionHandler:^(NSError *loadAndPresentError) {
                  // ...

                  // Consent has been gathered.

                  // Show the button if privacy options are required.
                  strongSelf.privacySettingsButton.enabled = isPrivacyOptionsRequired;
                }];
          }];
}

// Present the privacy options form when a user interacts with your
// privacy settings button.
- (IBAction)privacySettingsTapped:(UIBarButtonItem *)sender {
  [UMPConsentForm presentPrivacyOptionsFormFromViewController:self
                                completionHandler:^(NSError *_Nullable formError) {
                                  if (formError) {
                                    // Handle the error.
                                  }
                                }];
}

测试

如果您希望在开发过程中测试应用中的集成,请按照以下步骤以编程方式注册测试设备。在发布应用之前,请务必移除设置这些测试设备 ID 的代码。

  1. 致电 requestConsentInfoUpdateWithParameters:completionHandler:
  2. 检查日志输出中是否有类似于以下示例的消息,该消息显示了您的设备 ID 以及如何将其添加为测试设备:

    <UMP SDK>To enable debug mode for this device, set: UMPDebugSettings.testDeviceIdentifiers = @[2077ef9a63d2b398840261c8221a0c9b]
    
  3. 将测试设备 ID 复制到剪贴板。

  4. 修改代码,将 调用UMPDebugSettings().testDeviceIdentifiers 并传入 您的测试设备 ID 列表。

    Swift

    let parameters = UMPRequestParameters()
    let debugSettings = UMPDebugSettings()
    debugSettings.testDeviceIdentifiers = ["TEST-DEVICE-HASHED-ID"]
    parameters.debugSettings = debugSettings
    // Include the UMPRequestParameters in your consent request.
    UMPConsentInformation.sharedInstance.requestConsentInfoUpdate(
        with: parameters,
        completionHandler: { error in
          ...
        })
    

    Objective-C

    UMPRequestParameters *parameters = [[UMPRequestParameters alloc] init];
    UMPDebugSettings *debugSettings = [[UMPDebugSettings alloc] init];
    debugSettings.testDeviceIdentifiers = @[ @"TEST-DEVICE-HASHED-ID" ];
    parameters.debugSettings = debugSettings;
    // Include the UMPRequestParameters in your consent request.
    [UMPConsentInformation.sharedInstance
        requestConsentInfoUpdateWithParameters:parameters
                            completionHandler:^(NSError *_Nullable error){
                              ...
    }];
    

强制指定地理位置

UMP SDK 提供了一种方法,可让您使用 the debugGeography property of type UMPDebugGeography on UMPDebugSettings测试应用的行为,就如同设备位于欧洲经济区 (EEA) 或英国一样。请注意,调试设置仅适用于测试设备。

Swift

let parameters = UMPRequestParameters()
let debugSettings = UMPDebugSettings()
debugSettings.testDeviceIdentifiers = ["TEST-DEVICE-HASHED-ID"]
debugSettings.geography = .EEA
parameters.debugSettings = debugSettings
// Include the UMPRequestParameters in your consent request.
UMPConsentInformation.sharedInstance.requestConsentInfoUpdate(
    with: parameters,
    completionHandler: { error in
      ...
    })

Objective-C

UMPRequestParameters *parameters = [[UMPRequestParameters alloc] init];
UMPDebugSettings *debugSettings = [[UMPDebugSettings alloc] init];
debugSettings.testDeviceIdentifiers = @[ @"TEST-DEVICE-HASHED-ID" ];
debugSettings.geography = UMPDebugGeographyEEA;
parameters.debugSettings = debugSettings;
// Include the UMPRequestParameters in your consent request.
[UMPConsentInformation.sharedInstance
    requestConsentInfoUpdateWithParameters:parameters
                         completionHandler:^(NSError *_Nullable error){
                           ...
}];

使用 UMP SDK 测试应用时,您可能会发现重置 SDK 的状态很有用,这样您就可以模拟用户的首次安装体验。为此,SDK 提供了 reset 方法。

Swift

UMPConsentInformation.sharedInstance.reset()

Objective-C

[UMPConsentInformation.sharedInstance reset];

GitHub 上的示例

UMP SDK 集成示例: Swift | Objective-C